标签:quicksort tag 代码 art 函数 依次 i++ swa else
最近忙着准备找工作,把之前写的排序算法整理下,写到一起,方便以后用,废话不说,直接上代码;
#include<iostream>
#include<time.h>
using namespace std;
#define N 100
//#define SWAP(x,y){int t;t=x;x=y;y=t;}
#define SWAP(x,y) {x=x^y;y=x^y;x=x^y;}
//基数排序
void radixsort(int data[], int n)
{
//辅助函数,求数据的最大位数
int d = 1; //保存最大的位数
int p = 10;
for(int i = 0; i < n; ++i)
{
while(data[i] >= p)
{
p *= 10;
++d;
}
}
//基数排序
int *tmp = new int[n];
int *count = new int[10]; //计数器
int i, j, k;
int radix = 1;
for(i = 1; i <= d; i++) //进行d次排序
{
for(j = 0; j < 10; j++)
count[j] = 0; //每次分配前清空计数器
for(j = 0; j < n; j++)
{
k = (data[j] / radix) % 10; //统计每个桶中的记录数
count[k]++;
}
for(j = 1; j < 10; j++)
count[j] = count[j - 1] + count[j]; //将tmp中的位置依次分配给每个桶
for(j = n - 1; j >= 0; j--) //将所有桶中记录依次收集到tmp中
{
k = (data[j] / radix) % 10;
tmp[count[k] - 1] = data[j];
count[k]--;
}
for(j = 0; j < n; j++) //将临时数组的内容复制到data中
data[j] = tmp[j];
radix = radix * 10;
}
delete[]tmp;
delete[]count;
}
//shell排序,改进的插入排序
int shellsort(int *number)
{
for(int group=N/2;group>0;group/=2)
{
for(int i=group;i<N;i++)//每一个都循环,所以下面每次只交换一次
{
for(int j=i-group;j>=0&&(number[j]>number[j+group]);j-=group)//每次只能交换一次,交换多了就不对了
{
SWAP(number[j],number[j+group]);
}
}
}
return 0;
}
//插入排序
int insort(int *number)
{
/*int temp;
for(int i=N-2;i>=0;i--)//从大到小循环进行排序
{
temp=number[i];
int j=i+1;
while(temp>number[j])
{
number[j-1]=number[j];
j++;
if(j==N)
break;
}
number[j-1]=temp;
}*/
int temp,j;
for(int i=1;i<N;i++)//从小到大循环进行排序
{
temp=number[i];
for(j=i;j>0;j--)
{
if(number[j-1]>temp)
{
number[j]=number[j-1];
}
else
{
break;
}
}
number[j]=temp;
}
return 0;
}
//heap算法,堆排序,改进的选择排序
int heapsort(int *number)
{
//建立排序堆积树
int heap[N+1]={-1111},child,parent;
for(int i=1;i<=N;i++)
{
heap[i]=number[i-1];
child=i;
parent=i/2;
while(heap[child]<heap[parent]&&child>=2)//子树比根小并且有子树
{
SWAP(heap[child],heap[parent]);
child=parent;
parent=child/2;
}
}
//堆排序
int n=N;
while(n>1)
{
number[N-n]=heap[1];
SWAP(heap[1],heap[n]);
n--;
parent=1;
child=2*parent;
while(child<=n)
{
if(child<n&&heap[child]>heap[child+1])//有两个子树并右子树较小或
child++;
if(heap[parent]<=heap[child])//根比子树小
break;
SWAP(heap[parent],heap[child]);
parent=child;
child=2*parent;
}
}
number[N-1]=heap[1];
return 0;
}
//选择排序
int selsort(int *number)
{
int temp;
for(int i=0;i<N;i++)
{
int min=9999;
for(int j=i;j<N;j++)
{
if(min>number[j])
{
min=number[j];
temp=j;
}
}
number[temp]=number[i];
number[i]=min;
}
return 0;
}
//shaker排序,改进的冒泡排序
int shakersort(int *number)
{
int left=0,right=N-1,i;
int shift=left;
while(left<right)
{
for(i=left;i<right;i++)
{
if(number[i]>number[i+1])
{
SWAP(number[i],number[i+1]);
shift=i;
}
}
right=shift;
for(i=right;i>left;i--)
{
if(number[i]<number[i-1])
{
/*temp=number[i];
number[i]=number[i-1];
number[i-1]=temp;*/
SWAP(number[i],number[i-1]);
shift=i;
}
}
left=shift;
}
return 0;
}
//冒泡排序
int bubsort(int *number)
{
//int temp;
for(int i=0;i<N-1;i++)
{
for(int j=0;j<N-i-1;j++)
{
if(number[j]>number[j+1])
{
SWAP(number[j],number[j+1]);
}
}
}
return 0;
}
//快速排序1(最左为轴)
void quicksort1(int *number,int left,int right)
{
int s,i,j;
if(left<right)
{
s=number[left],i=left,j=right+1;
while(1)
{
while(i+1<right+1&&number[++i]<s) ;
while(j-1>left-1&&number[--j]>s) ;
if(i>=j)
break;
SWAP(number[i],number[j]);
}
number[left]=number[j];
number[j]=s;
quicksort1(number,left,j-1);
quicksort1(number,j+1,right);
}
}
//快速排序2(中间为轴)
void quicksort2(int *number,int left,int right)
{
int i,j,s;
if(left<right)
{
s=number[(left+right)/2],j=right+1,i=left-1;
while(1)
{
while(number[++i]<s) ;
while(number[--j]>s) ;
if(i>=j)
break;
SWAP(number[i],number[j]);
}
quicksort2(number,left,i-1);
quicksort2(number,j+1,right);
}
}
//算法导论书
void quicksort3(int *number,int left,int right)
{
int i,j,s,q;
if(left<right)
{
s=number[right];
i=left-1;
for(j=left;j<right;j++)
{
if(number[j]<=s)//当两个数一样的时候交换后为0
{
i++;
if(number[i]!=number[j])
//cout<<number[i]<<‘ ‘<<number[j]<<endl;
SWAP(number[i],number[j]);
//cout<<number[i]<<‘ ‘<<number[j]<<endl;
}
}
if(number[i+1]!=number[right])
SWAP(number[i+1],number[right]);
q=i+1;
quicksort3(number,left,q-1);
quicksort3(number,q+1,right);
}
}
//归并排序
int mergeSort(int *data, int p, int r)
{
int q;
int n1, n2, i, j, k;
if(p < r) //只有一个或无记录时不须排序
{
q = (int)((p+r)/2); //将data数组分成两半
mergeSort(data, p, q); //递归拆分左数组
mergeSort(data, q+1, r); //递归拆分右数组
//*************************合并数组
int *left=NULL, *right=NULL;
n1 = q-p+1;
n2 = r-q;
left = (int *)malloc(sizeof(int)*(n1));
right = (int *)malloc(sizeof(int)*(n2));
//检查是否分配成功
if(left==NULL||right==NULL){
cout<<"归并排序分配内存错误!!!"<<endl;
return 0;
}
for(i=0; i<n1; i++) //对左数组赋值
left[i] = data[p+i];
for(j=0; j<n2; j++) //对右数组赋值
right[j] = data[q+1+j];
i = j = 0;
k = p;
while(i<n1 && j<n2) //将数组元素值两两比较,并合并到data数组
{
if(left[i] <= right[j])
data[k++] = left[i++];
else
data[k++] = right[j++];
}
for(; i<n1; i++) //如果左数组有元素剩余,则将剩余元素合并到data数组
data[k++] = left[i];
for(; j<n2; j++) //如果右数组有元素剩余,则将剩余元素合并到data数组
data[k++] = right[j];
free(left);
free(right);
left=NULL;
right=NULL;
//当不需要再使用申请的内存时,记得释放;
//释放后应该把指向这块内存的指针指向NULL,防止程序后面不小心使用了它。
}
return 0;
}
int selectag()
{
cout<<"输入0为退出,"<<endl
<<"输入1为冒泡排序,"<<endl
<<"输入2为选择排序,"<<endl
<<"输入3为插入排序,"<<endl
<<"输入4为希尔排序(改进的插入排序),"<<endl
<<"输入5为Shaker排序(改进的冒泡排序),"<<endl
<<"输入6为heap(堆)排序(改进的选择排序),"<<endl
<<"输入7为快速排序1(最左为轴),"<<endl
<<"输入8为快速排序2(中间为轴),"<<endl
<<"输入9为快速排序3(算法导论),"<<endl
<<"输入10为归并排序,"<<endl
<<"输入11为基数排序,"<<endl
<<"请选择排序算法:";
return 0;
}
int creatlist(int *number)
{
int j,temp;
for(int i=0;i<N;i++)//随机生成1到N的数组
{
j=rand()%N;
temp=number[i];
number[i]=number[j];
number[j]=temp;
}
cout<<"排序前:"<<endl;
for(int i=0;i<N;i++)
{
cout<<number[i];
if(i<N-1)
cout<<"->";
}
cout<<endl;
return 0;
}
int main()
{
clock_t start, finish;//开始结束时间
double duration; //耗时
int number[N];
for(int i=0;i<N;i++)
number[i]=i;
srand((unsigned)time(NULL));
selectag();
int in=1,sortstatus=1;//sortstatus为是否进行了排序
char end;//是否退出循环
int inright=1;//输入正确
while(in!=0)
{
sortstatus=1;
while(inright)
{
cin.clear();//重置错误输入
cin.sync();//清空缓冲区 不然会出现无限循环
cin>>in;
if(!cin.fail())//如果输入不匹配,fail()会返回真
{
inright=0;
}
else
{
cout<<"**********************输入有误,不是int类型,请输入int数字:";
selectag();
}
}
start = clock(); //开始计时
switch(in)
{
case 0:
cout<<"**********************确认退出???(y/n)**********************"<<endl;
cin.clear();
cin>>end;
switch(end)
{
case ‘y‘:case ‘Y‘:
//这里退出,所以不用selectag();
break;
case ‘n‘:case ‘N‘:
selectag();
inright=1;//重新进行输入检测
sortstatus=0;//这次没有进行排序
in=9999;
break;
}
break;
case 1:
creatlist(number);
bubsort(number);
cout<<"冒泡排序:"<<endl;
break;
case 2:
creatlist(number);
selsort(number);
cout<<"选择排序:"<<endl;
break;
case 3:
creatlist(number);
insort(number);
cout<<"插入排序:"<<endl;
break;
case 4:
creatlist(number);
shellsort(number);
cout<<"希尔排序(改进的插入排序):"<<endl;
break;
case 5:
creatlist(number);
shakersort(number);
cout<<"Shaker排序(改进的冒泡排序):"<<endl;
break;
case 6:
creatlist(number);
heapsort(number);
cout<<"heap(堆)排序(改进的选择排序):"<<endl;
break;
case 7:
creatlist(number);
quicksort1(number,0,N-1);
cout<<"快速排序1(最左为轴):"<<endl;
break;
case 8:
creatlist(number);
quicksort2(number,0,N-1);
cout<<"快速排序2(中间为轴):"<<endl;
break;
case 9:
creatlist(number);
quicksort3(number,0,N-1);
cout<<"快速排序3(算法导论):"<<endl;
break;
case 10:
creatlist(number);
mergeSort(number,0,N-1);
cout<<"归并排序:"<<endl;
break;
case 11:
creatlist(number);
radixsort(number,N);
cout<<"基数排序:"<<endl;
break;
default:
sortstatus=0;
inright=1;
cout<<"**********************输入有误,请输入正确的数字!!!**********************"<<endl;
selectag();
break;
}
finish = clock(); //结束计时
duration=(double)(finish-start)/CLOCKS_PER_SEC;
cout<<"本算法总耗时"<<duration<<endl;
if(in!=0&&sortstatus)
{
for(int i=0;i<N;i++)
{
cout<<number[i];
if(i<N-1)
cout<<"->";
}
cout<<endl;
selectag();
inright=1;
}
}
system("pause");
return 0;
}
标签:quicksort tag 代码 art 函数 依次 i++ swa else
原文地址:http://www.cnblogs.com/jhmu0613/p/6780741.html