实现min函数
Implementing min function
您好,我发现了这个优先级队列实现,我正在尝试获得它的最小版本(而不是最大版本)。我不知道从哪里开始。我试着混合函数的符号(天真的尝试),但并没有让我走多远。任何关于如何实现它的帮助和几句解释它的话都是非常好的。来源如下:注意我已经留下了它的评论
#include <iostream>
#include <vector>
#include <assert.h>
using namespace std;
class PriorityQueue
{
vector<int> pq_keys;
void shiftRight(int low, int high);
void shiftLeft(int low, int high);
void buildHeap();
public:
PriorityQueue(){}
PriorityQueue(vector<int>& items)
{
pq_keys = items;
buildHeap();
}
/*Insert a new item into the priority queue*/
void enqueue(int item);
/*Get the maximum element from the priority queue*/
int dequeue();
/*Just for testing*/
void print();
};
void PriorityQueue::enqueue(int item)
{
pq_keys.push_back(item);
shiftLeft(0, pq_keys.size() - 1);
return;
}
int PriorityQueue::dequeue()
{
assert(pq_keys.size() != 0);
int last = pq_keys.size() - 1;
int tmp = pq_keys[0];
pq_keys[0] = pq_keys[last];
pq_keys[last] = tmp;
pq_keys.pop_back();
shiftRight(0, last-1);
return tmp;
}
void PriorityQueue::print()
{
int size = pq_keys.size();
for (int i = 0; i < size; ++i)
cout << pq_keys[i] << " ";
cout << endl;
}
void PriorityQueue::shiftLeft(int low, int high)
{
int childIdx = high;
while (childIdx > low)
{
int parentIdx = (childIdx-1)/2;
/*if child is bigger than parent we need to swap*/
if (pq_keys[childIdx] > pq_keys[parentIdx])
{
int tmp = pq_keys[childIdx];
pq_keys[childIdx] = pq_keys[parentIdx];
pq_keys[parentIdx] = tmp;
/*Make parent index the child and shift towards left*/
childIdx = parentIdx;
}
else
{
break;
}
}
return;
}
void PriorityQueue::shiftRight(int low, int high)
{
int root = low;
while ((root*2)+1 <= high)
{
int leftChild = (root * 2) + 1;
int rightChild = leftChild + 1;
int swapIdx = root;
/*Check if root is less than left child*/
if (pq_keys[swapIdx] < pq_keys[leftChild])
{
swapIdx = leftChild;
}
/*If right child exists check if it is less than current root*/
if ((rightChild <= high) && (pq_keys[swapIdx] < pq_keys[rightChild]))
{
swapIdx = rightChild;
}
/*Make the biggest element of root, left and right child the root*/
if (swapIdx != root)
{
int tmp = pq_keys[root];
pq_keys[root] = pq_keys[swapIdx];
pq_keys[swapIdx] = tmp;
/*Keep shifting right and ensure that swapIdx satisfies
heap property aka left and right child of it is smaller than
itself*/
root = swapIdx;
}
else
{
break;
}
}
return;
}
void PriorityQueue::buildHeap()
{
/*Start with middle element. Middle element is chosen in
such a way that the last element of array is either its
left child or right child*/
int size = pq_keys.size();
int midIdx = (size -2)/2;
while (midIdx >= 0)
{
shiftRight(midIdx, size-1);
--midIdx;
}
return;
}
int main()
{
//example usage
PriorityQueue asd;
asd.enqueue(2);
asd.enqueue(3);
asd.enqueue(4);
asd.enqueue(7);
asd.enqueue(5);
asd.print();
cout<< asd.dequeue() << endl;
asd.print();
return 0;
}
通常在此类问题中,即基于元素比较的算法中,您可以重新定义(a < b)
的含义。(顺便说一句,标准库中的东西就是这样工作的。你可以定义自己的比较器。)
所以如果你把它的意思改成相反的意思。您将颠倒顺序。
你需要识别每个元素的比较,并切换它
/*if child is bigger than parent we need to swap*/
if (pq_keys[childIdx] > pq_keys[parentIdx])
颠倒它的意义/逻辑。
简单的否定应该起作用:
/*if child is NOT bigger than parent we need to swap*/
if !(pq_keys[childIdx] > pq_keys[parentIdx])
你们甚至不需要理解算法。只是较小元素的相反含义。
编辑:附加说明。实际上,您可以将它重构为某种bool compare(T a, T b)
。在使用比较的情况下使用此函数。因此,每当你想改变行为时,你只需要改变一个地方,它就会始终如一。但这主要是为了避免寻找每一个这样的事件,以及愚蠢的错误和你错过的错误。
更简单:
std::prioroty_queue<int, std::vector<int>, std::greater<int>> my_queue;
如果这是练习的一部分,那么我建议遵循标准库的设计原则:将问题分解:
- 数据存储(例如std::vector)
- 排序或"堆积"算法(参见
std::make_heap
等) - 订购标准(由2。以上)
你的课应该给你一些余地,让你独立地改变其中的任何一个。有了这一点,您可以简单地将"小于"的排序更改为"大于"的排序。
相关文章:
- "error: no matching function for call to"构造函数错误
- 什么时候调用组成单元对象的析构函数
- 继承函数的重载解析
- 为什么随机数生成器不在void函数中随机化数字,而在main函数中随机化
- C++模板来检查友元函数的存在
- 为什么 -mmacosx-version-min=10.10 不阻止使用标记为从 10.11 开始的函数?
- 第 5 行:字符 54:错误:调用"min(int,std::__cxx11::basic_string<char>::size_type)"没有匹配函数
- 如何使用函数std::min()来计算最小值
- 在函数 'int main(int, char**) 中,没有声明 'MIN'
- 函数读取最大和min int值,并用文本字符串返回
- 在调试中,如何知道对函数的重复调用中参数的统计数据(max-min,average,distribution..)
- 为什么 std::numeric_limits<float>::min() 在流式传输到具有不同函数的输出时行为不同?
- min()函数的副作用
- 实现min函数
- 使用 std::initializer_list 使函数指向 std::min
- SSE 中的高效 min() 函数
- 为什么<T>编译器将 numeric_limits::min 解释为函数指针?
- 这个min()函数是如何工作的
- 调用'min(uint8_t&, int)'没有匹配函数
- 错误:没有匹配函数调用"min(长期无符号 int&,无符号 int&)"