shell排序是插入排序的优化,当需要排序的数据量比较大的时候,比较有帮助。
shell排序是一种分组排序,所以重点不同在于分组。如分组的大小初始值为长度的一般,每次分组的大小为之前的一般,直到为1.
原始数列 5 3 7 4 3 9 6 2 10 4 3 7 1 长度13
第一次分组6 5 6 1
1 5 6
3 2
2 3
7 10
7 10
4 4
4 4
3 3
3 3
9 7
7 9
将上面的红色的数字按照下面截图所示的顺序就是第一次分组的排序了。
排好序后:1 2 7 4 3 7 5 3 10 4 3 9 6
下面的就依次类推。
第二次分组3 1 2 7 4 3 7 5 3 10 4 3 9 6
1 4 5 4 6
2 3 3 3
7 7 10 9
排好序后:1 2 7 4 3 7 4 3 9 5 3 10 6
第三次分组1 1 2 7 4 3 7 5 3 10 4 3 9 6
此时直接使用插入排序即可。
排好序后:1 2 3 3 3 4 4 5 6 7 7 9 10
完整的测试程序:
#include "stdafx.h"
#include <iostream>
using namespace std;
void shell_ascending_sort(int data[], int n)
{
int i = 0, j = 0, temp = 0, d = 0;
for (i = n/2; i > 0; i = i/2)//控制增量,每次增量都减少一半
{
for (j = i; j < n; j++)
{
temp = data[j];
for (d = j - i; d >= 0 && temp < data[d]; d-=i)
{
data[d + i] = data[d];
}
data[d + i] = temp;
}
}
}
void shell_desending_sort(int data[], int n)
{
int i = 0, j = 0, temp = 0, d = 0;
for (i = n / 2; i > 0; i = i / 2)//控制增量,每次增量都减少一半
{
for (j = i; j < n; j++)
{
temp = data[j];
for (d = j - i; d >= 0 && temp > data[d]; d -= i)
{
data[d + i] = data[d];
}
data[d + i] = temp;
}
}
}
void print(int data[], int n)
{
for (int i = 0; i < n; i++)
{
cout << data[i] << " ";
}
cout << endl;
}
int main()
{
int num[] = {5,3, 7,4,3,9,6,2,10,4,3,7,1};
int len = sizeof(num) / sizeof(int);
cout << "data count:"<< len << ". before sort: ";
print(num, len);
shell_ascending_sort(num, len);
cout << "after sort: ";
print(num, len);
shell_desending_sort(num, len);
cout << "after desending sort: ";
print(num, len);
return 0;
}
测试结果:
data count:13. before sort: 5 3 7 4 3 9 6 2 10 4 3 7 1
6 :1 2 7 4 3 7 5 3 10 4 3 9 6
3 :1 2 7 4 3 7 4 3 9 5 3 10 6
1 :1 2 3 3 3 4 4 5 6 7 7 9 10
after sort: 1 2 3 3 3 4 4 5 6 7 7 9 10
6 :10 5 6 7 7 9 4 2 3 3 3 4 1
3 :10 7 9 7 5 6 4 3 4 3 2 3 1
1 :10 9 7 7 6 5 4 4 3 3 3 2 1
after desending sort: 10 9 7 7 6 5 4 4 3 3 3 2 1
请按任意键继续. . .