题目:输入n个整数,输出其中最小的k个。
例如输入1,2,3,4,5,6,7和8这8个数字,则最小的4个数字为1,2,3和4。
例如输入1,2,3,4,5,6,7和8这8个数字,则最小的4个数字为1,2,3和4。
不多说了,这个题是一个老题了,最简单的办法就是用大顶堆了,每次遍历数组与堆顶元素进行比较,如果比堆顶小,就替换堆顶,继续调整为大顶堆。
代码如下:
#pragma once
#include <cstdlib>
using namespace std;
template <typename T>
class MaxHeap
{
public:
MaxHeap(int size = 10)
{
this->size = size;
data = new T[size];
cur = 0;
}
MaxHeap(T a[], int size)
{
this->size = size;
data = new T[size];
for (int i = 0; i < size; i++)
data[i] = a[i];
cur = size;
BuildHeap();
}
T RemoveMax()
{
if (IsEmpty())
throw "heap is empty";
else
{
T temp = data[0];
data[0] = data[--cur];
if (cur > 0)
ShiftDown(0);
return temp;
}
}
void ReplaceMax(const T& value)
{
if (IsEmpty())
throw "heap is empty";
else
{
data[0] = value;
ShiftDown(0);
}
}
T PeekMax()
{
if (IsEmpty())
throw "heap is empty";
else
return data[0];
}
bool Insert(const T& value)
{
if (IsFull())
return false;
else
{
data[cur++] = value;
ShiftUp(cur - 1);
return true;
}
}
bool IsFull()
{
return cur == size;
}
bool IsEmpty()
{
return cur == 0;
}
~MaxHeap()
{
delete[] data;
}
private:
int size;
int cur;
T * data;
int LeftChild(int pose) const
{
return 2*pose + 1;
}
int RightChild(int pose) const
{
return 2*pose + 2;
}
int Parent(int pose) const
{
return (pose - 1) / 2;
}
// 从pose的位置向下调整
void ShiftDown(int pose)
{
int i = pose;
int j = LeftChild(i);
T temp = data[i];
while (j < cur)
{
if (j < cur - 1 && data[j] < data[j+1])
j++;
if (temp < data[j])
{
data[i] = data[j];
i = j;
j = LeftChild(j);
}
else
break;
}
data[i] = temp;
}
void ShiftUp(int pose)
{
int tempPose = pose;
T temp = data[tempPose];
while (tempPose > 0 && data[Parent(tempPose)] < temp)
{
data[tempPose] = data[Parent(tempPose)];
tempPose = Parent(tempPose);
}
data[tempPose] = temp;
}
void BuildHeap()
{
for (int i = cur/2 -1; i >= 0; i--)
ShiftDown(i);
}
};
#include <cstdlib>
using namespace std;
template <typename T>
class MaxHeap
{
public:
MaxHeap(int size = 10)
{
this->size = size;
data = new T[size];
cur = 0;
}
MaxHeap(T a[], int size)
{
this->size = size;
data = new T[size];
for (int i = 0; i < size; i++)
data[i] = a[i];
cur = size;
BuildHeap();
}
T RemoveMax()
{
if (IsEmpty())
throw "heap is empty";
else
{
T temp = data[0];
data[0] = data[--cur];
if (cur > 0)
ShiftDown(0);
return temp;
}
}
void ReplaceMax(const T& value)
{
if (IsEmpty())
throw "heap is empty";
else
{
data[0] = value;
ShiftDown(0);
}
}
T PeekMax()
{
if (IsEmpty())
throw "heap is empty";
else
return data[0];
}
bool Insert(const T& value)
{
if (IsFull())
return false;
else
{
data[cur++] = value;
ShiftUp(cur - 1);
return true;
}
}
bool IsFull()
{
return cur == size;
}
bool IsEmpty()
{
return cur == 0;
}
~MaxHeap()
{
delete[] data;
}
private:
int size;
int cur;
T * data;
int LeftChild(int pose) const
{
return 2*pose + 1;
}
int RightChild(int pose) const
{
return 2*pose + 2;
}
int Parent(int pose) const
{
return (pose - 1) / 2;
}
// 从pose的位置向下调整
void ShiftDown(int pose)
{
int i = pose;
int j = LeftChild(i);
T temp = data[i];
while (j < cur)
{
if (j < cur - 1 && data[j] < data[j+1])
j++;
if (temp < data[j])
{
data[i] = data[j];
i = j;
j = LeftChild(j);
}
else
break;
}
data[i] = temp;
}
void ShiftUp(int pose)
{
int tempPose = pose;
T temp = data[tempPose];
while (tempPose > 0 && data[Parent(tempPose)] < temp)
{
data[tempPose] = data[Parent(tempPose)];
tempPose = Parent(tempPose);
}
data[tempPose] = temp;
}
void BuildHeap()
{
for (int i = cur/2 -1; i >= 0; i--)
ShiftDown(i);
}
};