您的位置:首页 > 其它

HDU 3743 归并排序模板题

2015-11-12 15:49 253 查看

归并排序续讲

先贴代码

long long count = 0;
int a[1000000 + 5];
int b[1000000 + 5];
void Merge(int sourceArr[], int tempArr[], int starIndex, int midIndex, int endIndex)
{
int i = starIndex;
int j = midIndex + 1;
int k = starIndex;

while (i != midIndex + 1 && j != endIndex + 1)
{
if (sourceArr[i] < sourceArr[j])
tempArr[k++] = sourceArr[i++];
else
{
tempArr[k++] = sourceArr[j++];
count += midIndex - i + 1;// *&*&*&*&*&*&*&*&*&
}
}
while (i != midIndex + 1)
tempArr[k++] = sourceArr[i++];

while (j != endIndex + 1)
tempArr[k++] = sourceArr[j++];
}

void Merge_sort(int sourceArr[], int tempArr[], int starIndex, int endIndex)
{
int midIndex;
if (starIndex < endIndex)
{
midIndex = (starIndex + endIndex) / 2;
Merge_sort(sourceArr, tempArr, starIndex, midIndex);
Merge_sort(sourceArr, tempArr, midIndex + 1, endIndex);
Merge(sourceArr, tempArr, starIndex, midIndex, endIndex);

}
}


上面的是标准的归并函数;

我们注意到在注释标记的地方加上了count来统计一个数值,这个数值代表的就是在排序中交换的总步骤。

下面是解释:

start\ 归并排序的过程实际是2个已经排好序的数列(A, B)进行合并(放入C数组)的过程,

在合并的过程中如果从A中选取数据,那么不计入步数统计,因为A数列默认在前,从前面选取数据不用交换

同理如果从B中拿数据就一定是从后面交换到前面的,也就是说一定经过了交换

如果是下面的直接放入C数组的元素是不用计入步数,因为在之前生成的时候就已经计入了步骤\end

对于解决交换次数 交换路径 等问题上文是一个时间复杂度为N log N的模板;

最后总代码

#include<stdio.h>
long long count = 0;
int a[1000000 + 5];
int b[1000000 + 5];
void Merge(int sourceArr[], int tempArr[], int starIndex, int midIndex, int endIndex)
{
int i = starIndex;
int j = midIndex + 1;
int k = starIndex;

while (i != midIndex + 1 && j != endIndex + 1)
{
if (sourceArr[i] < sourceArr[j])
tempArr[k++] = sourceArr[i++];
else
{
tempArr[k++] = sourceArr[j++];
count += midIndex - i + 1;
}
}
while (i != midIndex + 1)
tempArr[k++] = sourceArr[i++];

while (j != endIndex + 1)
tempArr[k++] = sourceArr[j++];
}

void Merge_sort(int sourceArr[], int tempArr[], int starIndex, int endIndex)
{
int midIndex;
if (starIndex < endIndex)
{
midIndex = (starIndex + endIndex) / 2;
Merge_sort(sourceArr, tempArr, starIndex, midIndex);
Merge_sort(sourceArr, tempArr, midIndex + 1, endIndex);
Merge(sourceArr, tempArr, starIndex, midIndex, endIndex);

}
}

int main(void)
{
int t, i, k, min, temp;

while (scanf_s("%d", &t) != EOF)
{
count = 0;
getchar();
for (i = 0; i < t; i++)
{
scanf_s("%d", &a[i]);
}
Merge_sort(a, b, 0,  t - 1);
min = count;
for (k = 0; k < t - 1; k++)
{
count = 0;
a[k + t] = a[k];
Merge_sort(a, b, k + 1, k + t);
if (count < min)
min = count;
}

printf("%d\n", min + 1);
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: