排序专题之分配排序
Posted 纯纯的心儿
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了排序专题之分配排序相关的知识,希望对你有一定的参考价值。
分配排序分两块,桶式排序和基数排序,基数排序是桶式排序的递进:
下面来看下这两种排序:
简单的说,桶式排序就是,先将序列的数字进行顺序计数,
然后遍历计数每个数字的起点(数字相同的已经合并),然后
从尾部向前扫描,得一个排序好的序列:
具体代码如下:
#include<iostream>
using namespace std;
int main()
int n;
cin>>n;
int s[10],a[10];
int count[50];
int max;
int t;
int i,j;
for(i=0;i<n;i++)
cin>>s[i];
a[i]=s[i];
for(i=0;i<50;i++)
count[i]=0;
for(i=0;i<n;i++)
count[s[i]]++;
for(i=0;i<50;i++)
count[i]=count[i]+count[i-1];
for(i=n-1;i>=0;i--)
s[--count[a[i]]]=a[i];
for(i=0;i<n;i++)
cout<<" "<<s[i];
return 0;
基数排序:
多关键字排序方法
最高位优先法(MSD):先对最高位关键字k1(如花色)排序,将序列分成若干子序列,
每个子序列有相同的k1值;然后让每个子序列对次关键字k2(如面值)排序,
又分成若干更小的子序列;依次重复,直至就每个子序列对最低位关键字kd排序;
最后将所有子序列依次连接在一起成为一个有序序列
最低位优先法(LSD):从最低位关键字kd起进行排序,然后再对高一位的关键字排序,
……依次重复,直至对最高位关键字k1排序后,便成为一个有序序列
MSD与LSD不同特点
按MSD排序,必须将序列逐层分割成若干子序列,然后对各子序列分别排序
按LSD排序,不必分成子序列,对每个关键字都是整个序列参加排序
;并且可不通过关键字比较,而通过若干次分配与收集实现排序
基数排序的顺序方法(d次桶式排序)
for(i=1;i<=d;i++)
for(j=0;j<r;j++)//桶置零
count[j]=0;
for(j=0;j<n;j++)//桶计数
k=(s[i]/ra)%r;
count[k]++;
for(j=1;j<r;j++)
count[j]=count[j]+count[j-1]; //统计
for(j=n-1;j>=0;j--) //桶式排序的倒序放入
k=(s[j]/ra)%r;
count[k]--;
a[count[k]]=s[j];
for(j=0;j<n;j++)//重新给予赋值 进入第二次桶式排序
s[j]=a[j];
ra*=r;//改变模,向左移一位
链式基数排序
基数排序:借助“分配”和“收集”对单逻辑关键字进行排序的一种方法
链式基数排序:用链表作存储结构的基数排序
链式基数排序步骤
设置10个队列,f[i]和e[i]分别为第i个队列的头指针和尾指针
第一趟分配对最低位关键字(个位)进行,改变记录的指针值,
将链表中记录分配至10个链队列中,每个队列记录的关键字的个位相同
第一趟收集是改变所有非空队列的队尾记录的指针域,
令其指向下一个非空队列的队头记录,重新将10个队列链成一个链表
重复上述两步,进行第二趟、第三趟分配和收集,分别对十位、百位进行,
最后得到一个有序序列
void distribute(record *a[],int first,int i,int r,staticqueue *queue) //分配过程
int j,k,a,curr=first;
for(j=0;j<r;j++)//初始化整个队列
queue[j].head=-1;
while(curr!=-1)//对整个静态链进行分配
k=a[curr].key; //取第i位的排序码数字k
for(a=0;a<i;a++)
k/=r;
k%=r;
if(queue[k].head==-1) //桶为空,则a[curr]为第一个记录
queue[k].head=curr;
else a[queue[k].tail].next=curr;
queue[k].tail=curr;
curr=a[curr].next;
void collect(record *a,int &first,int r,staticqueue *queue)//收集过程
int last,k=0;
while(queue[k].head==-1)//找到第一个非空队列
k++;
first=queue[k].head;
last=queue[k].tail;
while(k<r-1)//继续收集下一个队列
k++;
while(k<r-1&&queue[k].head==-1)
k++;
if(queue[k].head!=-1)
a[last].next=queue[k].head;
last=queue[k].tail;
a[last].next=-1; //收集完毕
以上是关于排序专题之分配排序的主要内容,如果未能解决你的问题,请参考以下文章