优先队列的应用 C++实现

优先队列可以用堆来实现, 堆底层可以用数组表示,
通过索引关系,可以表示成一颗二叉完全树

C++的STL提供了相应的容器适配器
包含在queue头文件中

下面通过一道题来看如何使用它

给定一个字符串,请将字符串里的字符按照出现的频率降序排列。

string frequencySort(string s) {
}

首先,统计字符出现的频率,通过map容器可以很简单的统计出来

map<char, int> mp;

for (auto e : s)
{
    ++mp[e];
}

然后我们需要构建一个优先队列,而且要指定优先队列的排序方式
因此我们定义了一个自己的结构体, 并定义了<操作符(降序定义小于号,升序大于号),

struct Node
{
    Node(const pair<char, int> &val) : p(val) {}
    pair<char, int> p;
};

bool operator<(const Node &a, const Node &b)
{
    return a.p.second < b.p.second;
}

然后把键值对放入优先队列中

for (auto e : mp)
{
    pq.push(make_pair(e.first, e.second));
}

要用的时候,依次取出来就是了,每次取出的都是里面最大(或最小)的

string res;
while (!pq.empty())
{
    for (int i = 0; i < pq.top().p.second; ++i)
        res.push_back(pq.top().p.first);
    pq.pop();
}

还有好几个类似的题,都可以用这种方式解决

比如 :

下面是堆的实现, 还是建议掌握的

#include <vector>
using namespace std;

template <class T>
class Heap
{
  public:
    Heap(size_t maxElems)
    {
        h = new HeapStruct;
        h->Elems = new T[maxElems + 1];
        h->Capacity = maxElems;
        h->size = 0;
    }
    ~Heap()
    {
        destroy();
    }
    void insert(T x)
    {
        size_t i;
        if (isFull())
        {
            return;
        }
        for (i = ++h->size; i / 2 > 0 && h->Elems[i / 2] > x; i /= 2)
        {
            h->Elems[i] = h->Elems[i / 2];
        }
        h->Elems[i] = x;
    }
    T deleteMin()
    {
        size_t i, child;
        T minElems, lastElems;
        if (isEmpty())
            return h->Elems[0];
        minElems = h->Elems[1];
        lastElems = h->Elems[h->size--];
        for (i = 1; i * 2 <= h->size; i = child)
        {
            child = i * 2;
            if (child != h->size && h->Elems[child + 1] < h->Elems[child])
                ++child;
            if (lastElems > h->Elems[child])
                h->Elems[i] = h->Elems[child];
            else
                break;
        }
        h->Elems[i] = lastElems;
        return minElems;
    }
    bool isFull()
    {
        return h->size == h->Capacity;
    }
    bool isEmpty()
    {
        return h->size == 0;
    }
    T findMin()
    {
        return h->Elems[1];
    }

  private:
    void destroy()
    {
        delete h->Elems;
        delete h;
    }
    void makeEmpty() {}

    struct HeapStruct
    {
        size_t Capacity;
        size_t size;
        T *Elems;
    };
    HeapStruct* h;
};

版权声明:本文为kwebi原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://www.cnblogs.com/kwebi/p/9811990.html