非比较排序2:基数排序

一、基数排序

稳定排序

按位排序:从低位(个位)到高位,取序列中元素相应位数字计数排序

c++代码:

//供RadixSort用的计数排序
void CountSort1(vector<int>& sequence, vector<int> vec_digit, int max_k=9);

void RadixSort(vector<int>& sequence, int n_digit)
{
    const int c_len = sequence.size();
    int i,j;
    for(i=0; i<n_digit; ++i)
    {
            vector<int> vec_digit(c_len);
            for(j=0; j<c_len; ++j)
                    vec_digit[j] = sequence[j] / int(pow(10,i)) % 10;
            CountSort1(sequence, vec_digit);
    }
}

void CountSort1(vector<int>& sequence, vector<int> vec_digit, int max_k)
{
    vector<int> count(max_k+1,0);  // 计数数组,max_k为vec_digit元素的最大值
    const int c_len = sequence.size();
    vector<int> sort_seq(c_len);
    for(int i=0; i<c_len; ++i)
        ++count[vec_digit[i]];
    for(int i=1; i<=max_k; ++i)
        count[i] += count[i-1];
    for(int i=c_len-1; i>=0; --i)  //c_len->0维持稳定排序
    {
        sort_seq[count[vec_digit[i]]-1] = sequence[i];  //-1是因为下标从0开始
        --count[vec_digit[i]];  //使得后续与vec_digit[i]相同的元素的位置往前挪1
    }
    sequence = sort_seq;
}

空间复杂度:k待排序数据的最大位数,即代码中的n_digit

                S(n) = θ(n+k)  

时间复杂度:外层for循环次数 x 计数排序时间复杂度

                    由于基数排序中所用的计数排序max_k=9,所以其时间复杂度为θ(n+10)=θ(n)

                    T(n) = n_digit x θ(n) = θ(k*n)

 扩展:这里取位数的方式为十进制,可以根据实际情况取其他进制以使得效果更好(k越小,计数排序的max_k越大,即计数排序的时间复杂度越大) ;最大的进制数应小于等于lgn(以2为底)。            




猜你喜欢

转载自blog.csdn.net/qw_sunny/article/details/80657956