Una cola de prioridad es un tipo de datos abstracto que captura la idea de un contenedor cuyos elementos tienen "prioridades" adjuntas. Un elemento de máxima prioridad siempre aparece al principio de la cola. Si se elimina ese elemento, el siguiente elemento de mayor prioridad avanza al frente.
La biblioteca estándar de C ++ define una plantilla de clase priority_queue, con las siguientes operaciones:
push : inserta un elemento en la cola de prioridad.
top : Devuelve (sin eliminarlo) un elemento de mayor prioridad de la cola de prioridad.
pop : Elimina un elemento de mayor prioridad de la cola de prioridad.
tamaño : Devuelve el número de elementos en la cola de prioridad.
vacío : Devuelve verdadero o falso según si la cola de prioridad está vacía o no.
El siguiente fragmento de código muestra cómo construir dos colas de prioridad, una que puede contener números enteros y otra que puede contener cadenas de caracteres:
#include <queue>
priority_queue<int> q1;
priority_queue<string> q2;
El siguiente es un ejemplo de uso de la cola de prioridad:
#include <string>
#include <queue>
#include <iostream>
using namespace std;
int main()
{
piority_queue<string> pq;
pq.push("the quick");
pq.push("fox");
pq.push("jumped over");
pq.push("the lazy dog");
while (!pq.empty()) {
cout << pq.top() << endl;
pq.pop();
}
return 0;
}
El resultado de este programa es:
the quick
the lazy dog
jumped over
fox
Dado que una cola sigue una disciplina de prioridad, las cadenas se imprimen de mayor a menor prioridad.
A veces es necesario crear una cola de prioridad para contener objetos definidos por el usuario. En este caso, la cola de prioridad necesita conocer el criterio de comparación utilizado para determinar qué objetos tienen la mayor prioridad. Esto se hace mediante un objeto función perteneciente a una clase que sobrecarga al operador (). El sobrecargado () actúa como <con el propósito de determinar prioridades. Por ejemplo, supongamos que queremos crear una cola de prioridad para almacenar objetos de tiempo. Un objeto Time tiene tres campos: horas, minutos, segundos:
struct Time {
int h;
int m;
int s;
};
class CompareTime {
public:
bool operator()(Time& t1, Time& t2)
{
if (t1.h < t2.h) return true;
if (t1.h == t2.h && t1.m < t2.m) return true;
if (t1.h == t2.h && t1.m == t2.m && t1.s < t2.s) return true;
return false;
}
}
Una cola de prioridad para almacenar tiempos de acuerdo con el criterio de comparación anterior se definiría de la siguiente manera:
priority_queue<Time, vector<Time>, CompareTime> pq;
Here is a complete program:
#include <iostream>
#include <queue>
#include <iomanip>
using namespace std;
struct Time {
int h;
int m;
int s;
};
class CompareTime {
public:
bool operator()(Time& t1, Time& t2)
{
if (t1.h < t2.h) return true;
if (t1.h == t2.h && t1.m < t2.m) return true;
if (t1.h == t2.h && t1.m == t2.m && t1.s < t2.s) return true;
return false;
}
};
int main()
{
priority_queue<Time, vector<Time>, CompareTime> pq;
Time t[4] = { {3, 2, 40}, {3, 2, 26}, {5, 16, 13}, {5, 14, 20}};
for (int i = 0; i < 4; ++i)
pq.push(t[i]);
while (! pq.empty()) {
Time t2 = pq.top();
cout << setw(3) << t2.h << " " << setw(3) << t2.m << " " <<
setw(3) << t2.s << endl;
pq.pop();
}
return 0;
}
El programa imprime las horas de la última a la más antigua:
5 16 13
5 14 20
3 2 40
3 2 26
Si quisiéramos que los primeros tiempos tuvieran la máxima prioridad, redefiniríamos CompareTime de esta manera:
class CompareTime {
public:
bool operator()(Time& t1, Time& t2)
{
if (t2.h < t1.h) return true;
if (t2.h == t1.h && t2.m < t1.m) return true;
if (t2.h == t1.h && t2.m == t1.m && t2.s < t1.s) return true;
return false;
}
};