桶排序,基數排序
阿新 • • 發佈:2021-02-05
桶排序
這裡是百度百科桶排序介紹圖,排序方法描述就是:對於要排序的目標取值範圍在0~n-1的m個數,例項說明,排序3,5,6,1,2,4,3這7個數字,取值在0~9之間;
- 首先建立10個桶子,編號分別為0、1、2……9,
- 按照這7個數字,把他們分別放到相應編號的桶子中
- 從桶子中按順序收集資料
註明:源資料為按連結串列排列,每個桶子也是一個連結串列。
程式碼如下:
template<class T>
void chain<T>::binSort(int range)
{// Sort the nodes in the chain.
// create and initialize the bins
chainNode<T> **bottom, **top;
bottom = new chainNode<T>* [range + 1];
top = new chainNode<T>* [range + 1];
for (int b = 0; b <= range; b++)
bottom[b] = NULL;
// 把節點放到箱子中
// 箱排序是每個箱子往頭結點插入
for (; firstNode != NULL; firstNode = firstNode->next)
{// add firstNode to proper bin
int theBin = firstNode->element; // type conversion to int
if (bottom[theBin] == NULL) // 箱子是空的,直接把插入節點設為頭結點
bottom[theBin] = top[theBin] = firstNode;
else
{// bin not empty
top[theBin]->next = firstNode;
top[ theBin] = firstNode;
}
}
// collect from bins into sorted chain
// 把箱子中的節點收集到排序的連結串列中
chainNode<T> *y = NULL;
for (int theBin = 0; theBin <= range; theBin++)
if (bottom[theBin] != NULL)
{// bin not empty
if (y == NULL) // first nonempty bin
firstNode = bottom[theBin];
else // not first nonempty bin
y->next = bottom[theBin];
y = top[theBin];
}
if (y != NULL)
y->next = NULL;
//把用來排序的箱子空間釋放
delete [] bottom;
delete [] top;
}
基數排序
基數排序是桶排序的升級版
基數排序是多個桶排序,比如二位數的基數排序,取模10,然後對於個位、十位,有0~9共10個箱子,先按照各位排序,把整個數字放到桶子中,放到桶子中相應位置的編號為該數字的個位數,放進去之後,進行桶排序,結果是一個個位有序,而十位無序的表,然後把該表按照十位為其編號放到桶子中,桶排序,進行收集,之後的結果就是整體有序的數字了。
計算執行步數的話,例如對於取值在0~10^6的1000個數字,如果按照模1000的基數排序,一共需要兩次桶排序,每次桶排序共需要1000+1000+1000=3000個步驟,共2*3000=6000
為什麼是3000?
1000個桶子初始化->分配1000個整數->從1000個桶子中收集;
因此,如果按照模100的計數排序共需要3*(100+1000+100)=3600個執行步
把數分解為數字需要出發和取模操作。如果用基數10來分解,那麼從最低位到最高位的數字分解式為x%10;(x%100)/10;(x%1000)/100;……
template<class T>
int chain<T>::decompose(int value,int range,int time)
{
if(time == 1)
return value%range;
for(int i = 1; i < time; i++)
{
range *=10;
}
return (value%range)/(range/10);
}
template<class T>
void chain<T>::binSort(int range)
{
for(int time = 1;time < 3; time++)
{
// Sort the nodes in the chain.
// create and initialize the bins
chainNode<T> **bottom, **top;
bottom = new chainNode<T>* [range + 1];
top = new chainNode<T>* [range + 1];
for (int b = 0; b <= range; b++)
bottom[b] = NULL;
// 把節點放到箱子中
// 箱排序是每個箱子往頭結點插入
for (; firstNode != NULL; firstNode = firstNode->next)
{
// add firstNode to proper bin
int theBin = decompose(firstNode->element,range,time); // type conversion to int
if (bottom[theBin] == NULL) // 箱子是空的,直接把插入節點設為頭結點
bottom[theBin] = top[theBin] = firstNode;
else
{
// bin not empty
top[theBin]->next = firstNode;
top[theBin] = firstNode;
}
}
// collect from bins into sorted chain
// 把箱子中的節點收集到排序的連結串列中
chainNode<T> *y = NULL;
for (int theBin = 0; theBin <= range; theBin++)
if (bottom[theBin] != NULL)
{
// bin not empty
if (y == NULL) // first nonempty bin
firstNode = bottom[theBin];
else // not first nonempty bin
y->next = bottom[theBin];
y = top[theBin];
}
if (y != NULL)
y->next = NULL;
//把用來排序的箱子空間釋放
delete [] bottom;
delete [] top;
}
}
template<class T>
void chain<T>::RadixSort(int range)
{
// Sort the nodes in the chain
binSort(range);//對個位進行排序
}