1、小范围排序
已知一个几乎有序的数组,几乎有序是指,如果把数组排好顺序的话,每个元素移动的距离可以不超过k,并且k相对于数组来说比较小。
选择改进的堆排序。根据题意,最小值一定在A的前k(0~k-1)个元素内、次小值一定在A的第二组k(1~k)个元素内,以此类推,每次取原数组A的k个元素进行堆排序,然后把堆顶元素放入A的已排序序列中,(0~k-1)排序的堆顶赋值给A[0],(1~k)排序的堆顶赋值给A[1],以此类推。最后剩下A中最后的k个元素(k-n~n-1),进行标准的堆排序,第一次是K个元素的堆,排序后将堆顶赋值给A[n-k],紧接着把堆尾元素赋值给堆顶,再排序,此时只是k-1个元素的堆,依次类推,每次把堆顶元素放入A中已排序序列后,都把堆尾元素赋值到堆顶,同时堆的元素个数减1,直到堆的元素个数为1,整个排序结束。
class
ScaleSort {
public :
void
heapify(
int
* B,
int
i,
int
k) {
int
j,ex;
ex = B[i];
j = 2*i + 1;
while
(j < k) {
if (j + 1 < k && B[j + 1] < B[j])
j++;
if (B[j] >= ex)
break
;
B[i] = B[j];
i = j;
j = 2*i + 1;
}
B[i] = ex;
return
;
}
vector
<int> sortElement(
vector
<
int
> A,
int
n,
int
k) {
// write code here
int
m = 0,exc;
int
*temp =
new
int
[k];
for
(
int
l = 0;l < k;l++) {
temp[l] = A[l];
}
for
(
int
i = k/2-1;i >= 0;i--)
heapify(temp,i,k);
for
(
int
i = k;i < n;i++) {
A[i-k] = temp[0];
temp[0] = A[i];
heapify(temp,0,k);
}
for
(
int
j = n-k;j < n;j++) {
A[j] = temp[0];
k--;
temp[0] = temp[k];
heapify(temp,0,k);
}
delete
[]temp;
temp = NULL;
return
A;
}
};
2、求一个数组排序后相邻元素之差的最大值,时间复杂度为O(n)、空间复杂度为O(n)
若先排序后求差值则只有桶排序满足时间复杂度,但是桶排序不能满足空间复杂度,桶排序的空间复杂度为O(max-min)。因此要用改进的桶排序但是又没有真正的排序。
①、求出数组A的最大值max和最小值min,并把区间max-min平均分成n份,每份大小为interval,则只需要n+1个桶;
②、用A[i]-min/interval的整数部分确定A[i]该入的桶,并定义三个大小为n+1的数组,bucket记录n+1个桶每个桶的入桶元素个数,max_bucket记录每个桶中最大值,min_bucket记录每个桶中最小值;
③、遍历bucket数组,将后一个桶的最小值min_bucket[j]减去前一个桶的最大值max_bucket[j-1],记录下最大的差值,返回该差值。
int
maxGap(
vector
<
int
> A,
int
n) {
int
max = A[0],min = A[0];
for (
int
i = 1;i < n;i++) {
if (A[i] > max) max = A[i];
else
if (A[i] < min) min = A[i];
}
float
interval = (
float
)(max - min)/n;
int
bucket[n+1];
for (
int
j = 0;j < n+1;j++)
bucket[j] = 0;
for (
int
i = 0;i < n;i++) {
int
j = (
int
)(A[i]-min)/interval;
bucket[j]++;
min_bucket[j] = A[i];
max_bucket[j] = A[i];
}
for (
int
i = 0;i < n;i++) {
int
j = (
int
)(A[i]-min)/interval;
if (A[i] > max_bucket[j]) max_bucket[j] = A[i];
if (A[i] < min_bucket[j]) min_bucket[j] = A[i];
}
int
maxGap = 0;
for (
int
i = 0,j = 1;j < n+1;j++) {
if (bucket[j] > 0) {
if (min_bucket[j]-max_bucket[i] > maxGap)
maxGap = min_bucket[j] - max_bucket[i];
i = j;
}
}
return
maxGap;
}
};