zoukankan      html  css  js  c++  java
  • c++实现十大经典排序算法

      1 #include <iostream>
      2 #include <vector>
      3 
      4 std::vector<int> g_array {
      5     12, 3, 52, 65, 9, 29,16, 7, 2, 78, 63, 98, 23, 43, 1, 24, 84, 34, 94, 32
      6 };
      7 void Swap(std::vector<int>& array, int i, int j) {
      8     int temp = array[j];
      9     array[j] = array[i];
     10     array[i] = temp;
     11 }
     12 void ShowArray(std::vector<int>& array) {
     13     for (int i = 0; i < array.size(); ++i) {
     14         std::cout << array[i] << " ";
     15     }
     16     std::cout << "
    ";
     17 }
     18 
     19 // ----------------比较排序-----------------
     20 // 冒泡排序:交换,时间复杂度O(n)- O(n2),空间复杂度O(1)
     21 void BubbleSort(std::vector<int>& array);
     22 // 快速排序:分治法+交换+双重游标,时间复杂度O(nlogn) - O(n2),空间复杂度O(nlogn).递归算法每次都要存储栈信息,因此为nlogn
     23 void QuickSort(std::vector<int>& array, int begin, int end);
     24 // 插入排序:有序子序列 + 插入位置 + 连续数量移动,时间复杂度O(n) - O(n2),空间复杂度O(1)
     25 void InsertionSort1(std::vector<int>& array);   // 找到位置后移动
     26 void InsertionSort2(std::vector<int>& array);   // 比较相邻元素,然后交互
     27 // shell 排序:宏观调控 + 增量子序列 + 增量减少至1。时间复杂度O(n1.3) - O(n2),空间复杂度O(1)。shell增量的选择是个数学难题,一般采用length/作为步长
     28 void ShellSort1(std::vector<int>& array);   // 找到位置后移动
     29 void ShellSort2(std::vector<int>& array);   // 比较相邻元素,然后交互
     30 // 选择排序.O(n2),空间复杂度O(1).找到最小元素,放到队列头,队列头有序。以此类推
     31 void SelectionSort(std::vector<int>& array);
     32 // 堆排序. 时间复杂度O(nlogn),空间复杂度O(nlogn)
     33 void HeapSort(std::vector<int>& array);
     34 // 归并排序.时间复杂度O(nlogn),空间复杂度O(nlogn)
     35 void MergeSort(std::vector<int>& array, int begin, int end);
     36 // -----------------非比较排序----------------
     37 // 计数排序.时间复杂度O(n+k),空间复杂度O(n+k),k是整数取值范围.快过任何比较排序算法,但是对空间要求较高,适用于有限小范围的区域
     38 void CountingSort(std::vector<int>& array, int max = 100);
     39 // 桶排序,是计数排序的升级版本。时间复杂度O(n+k) - O(n2),空间复杂度O(n+k),k是整数取值范围.快过任何比较排序算法,但是对空间要求较高,适用于有限小范围的区域
     40 // 计数排序申请的空间比较大,如果分散不均匀,很多空间未访问,会造成浪费。桶排序取出最大值和最小值的差值,划分成若干个 连续+范围递增 的数组,每个数组进行内部排序
     41 void BucketSort(std::vector<int>& array);
     42 // 基数排序.时间复杂度O(n*k),空间复杂度O(n+k)
     43 void RadixSort(std::vector<int>& array);
     44 
     45 int main() {
     46 //    BubbleSort(g_array);
     47 //    QuickSort(g_array, 0, g_array.size() - 1);
     48 //    InsertionSort2(g_array);
     49 //    ShellSort2(g_array);
     50 //    SelectionSort(g_array);
     51 //    HeapSort(g_array);
     52 //    MergeSort(g_array, 0, g_array.size() - 1);
     53 //    CountingSort(g_array);
     54 //    BucketSort(g_array);
     55     RadixSort(g_array);
     56     ShowArray(g_array);
     57     return 0;
     58 }
     59 
     60 void BubbleSort(std::vector<int>& array) {
     61     const size_t sz = array.size();
     62     if (sz <= 1) {
     63         return;
     64     }
     65     for (int i = 0; i < sz; ++i) {
     66         for (int j = 0; j < sz - i - 1; ++j) {
     67             if (array[j] > array[j + 1]) {
     68                 Swap(array, j, j + 1);
     69             }
     70         }
     71     }
     72 }
     73 
     74 void QuickSort(std::vector<int>& nums, int l ,int r) {
     75     if (l < r) {
     76         const int target = nums[l];
     77         int b = l + 1;
     78         int e = r;
     79         while (b < e)
     80         {
     81             if (nums[b] >= target && nums[e] < target) {
     82                 Swap(nums, b, e);
     83             }
     84             if (nums[b] < target) {
     85                 b++;
     86             }
     87             if (nums[e] >= target) {
     88                 e--;
     89             }
     90         }
     91         if (nums[l] > nums[b]) {
     92             Swap(nums, b, l);
     93         }
     94         QuickSort(nums, l, b - 1);
     95         QuickSort(nums, b, r);
     96     }
     97 }
     98 
     99 void InsertionSort1(std::vector<int> &array) {
    100     const size_t sz = array.size();
    101     if (sz <= 1) {
    102         return;
    103     }
    104     for (int i = 1; i < sz; ++i) {
    105         const int target = array[i];
    106         int j = i;
    107         for (; j > 0; --j) {
    108             if (array[j - 1] <= target) {
    109                 break;
    110             }
    111         }
    112         for (int k = i; k > j; --k) {
    113             array[k] = array[k - 1];
    114         }
    115         array[j] = target;
    116     }
    117 }
    118 
    119 void InsertionSort2(std::vector<int> &array) {
    120     const size_t sz = array.size();
    121     if (sz <= 1) {
    122         return;
    123     }
    124     for (int i = 1; i < sz; ++i) {
    125         const int target = array[i];
    126         int j = i;
    127         for (; j > 0 && array[j] < array[j - 1]; --j) {
    128             Swap(array, j, j -1);
    129         }
    130         array[j] = target;
    131     }
    132 }
    133 
    134 void ShellSort1(std::vector<int> &array) {
    135     const size_t sz = array.size();
    136     if (sz <= 1) {
    137         return;
    138     }
    139     for (int gap = sz/2; gap > 0; gap = gap/2) {
    140         for (int i = 0; i < gap; ++i) {
    141             // 对每组增量进行插入排序
    142             for (int j = i + gap; j < sz; j += gap) {
    143                 const int target = array[j];
    144                 int k = j;
    145                 for (; k > 0; k -= gap) {
    146                     if (array[k - gap] < target) {
    147                         break;
    148                     }
    149                 }
    150                 for (int l = j; l > k; l -= gap) {
    151                     array[l] = array[l - gap];
    152                 }
    153                 array[k] = target;
    154             }
    155         }
    156     }
    157 }
    158 
    159 void ShellSort2(std::vector<int> &array) {
    160     const size_t sz = array.size();
    161     if (sz <= 1) {
    162         return;
    163     }
    164     for (int gap = sz/2; gap > 0; gap = gap/2) {
    165         for (int i = gap; i < sz; ++i) {
    166             const int target = array[i];
    167             int j = i;
    168             for (; j >= gap && array[j] < array[j - gap]; j = j - gap) {
    169                 Swap(array, j, j - gap);
    170             }
    171             array[j] = target;
    172         }
    173     }
    174 }
    175 
    176 void SelectionSort(std::vector<int> &array) {
    177     const size_t sz = array.size();
    178     if (sz <= 1) {
    179         return;
    180     }
    181     for (int i = 0; i < sz; ++i) {
    182         int min = array[i];
    183         int index = i;
    184         for (int j = i; j < sz; ++j) {
    185             if (array[j] < min) {
    186                 min = array[j];
    187                 index = j;
    188             }
    189         }
    190         Swap(array, index, i);
    191     }
    192 }
    193 
    194 void AdjustHeap(std::vector<int> &array, int parent, int sz) {
    195     if (sz <= 1) {
    196         return;
    197     }
    198     const int left = parent*2 + 1;
    199     if (left >= sz) {
    200         return;
    201     } else {
    202         const int right = parent*2 + 2;
    203         if (right >= sz) {
    204             if (array[parent] < array[left]) {
    205                 Swap(array, parent, left);
    206                 AdjustHeap(array, left, sz);
    207             }
    208         } else {
    209             int max = array[right] < array[left] ? left : right;
    210             if (array[parent] < array[max]) {
    211                 Swap(array, parent, max);
    212                 AdjustHeap(array, max, sz);
    213             }
    214         }
    215     }
    216 }
    217 
    218 void HeapSort(std::vector<int> &array) {
    219     const size_t sz = array.size();
    220     if (sz <= 1) {
    221         return;
    222     }
    223     // 构建大顶堆
    224     for (int i = sz - 1; i > 0; i = i - 2) {
    225         const int parent = i/2;
    226         AdjustHeap(array, parent, sz);
    227     }
    228     // 交换最大元素到末尾
    229     for (int j = 1; j <= sz; ++j) {
    230         Swap(array, 0, sz - j);
    231         AdjustHeap(array, 0, sz - j);
    232     }
    233 }
    234 
    235 std::vector<int> temp;
    236 void MergeSort(std::vector<int> &array, int begin, int end) {
    237     const size_t sz = end - begin + 1;
    238     if (sz <= 1) {
    239         return;
    240     }
    241     int mid = (begin + end)/2;
    242     MergeSort(array, begin, mid);
    243     MergeSort(array, mid + 1, end);
    244 
    245     int left = begin;
    246     int right = mid + 1;
    247 
    248     temp.resize(sz);
    249     for (int i = begin; i <= end; ++i) {
    250         int min;
    251         if (left > mid) {
    252             min = right++;
    253         } else if (right > end) {
    254             min = left++;
    255         } else if (array[left] < array[right]) {
    256             min = left++;
    257         } else {
    258             min = right++;
    259         }
    260         temp.push_back(array[min]);
    261     }
    262     for (int i = begin; i <= end; ++i) {
    263         array[i] = temp[i - begin];
    264     }
    265 }
    266 
    267 void CountingSort(std::vector<int> &array, int max) {
    268     const size_t sz = array.size();
    269     if (sz <= 1) {
    270         return;
    271     }
    272     std::vector<int> count(max, 0);
    273     for (int i = 0; i < sz; ++i) {
    274         count[array[i]]++;
    275     }
    276     array.clear();
    277     array.reserve(sz);
    278     for (int j = 0; j < max; ++j) {
    279         while (count[j]-- > 0) {
    280             array.push_back(j);
    281         }
    282     }
    283 }
    284 
    285 void BucketSort(std::vector<int> &array) {
    286     const size_t sz = array.size();
    287     if (sz <= 1) {
    288         return;
    289     }
    290     int max = std::numeric_limits<int>::min();
    291     int min = std::numeric_limits<int>::max();
    292     for (int i = 0; i < sz; ++i) {
    293         if (array[i] > max) {
    294             max = array[i];
    295         }
    296         if (array[i] < min) {
    297             min = array[i];
    298         }
    299     }
    300     const int bucketCount = 1;
    301     std::vector<std::vector<int>> buckets;
    302     buckets.resize(bucketCount);
    303     const int bucketRangeIncrease = (max - min)/bucketCount + 1;    // 这里+1很重要
    304     for (int j = 0; j < sz; ++j) {
    305         // 采用相对法,保证(array[j] - min)一定>=0。如果带排序内有负数,则下标计算出来是负值
    306         buckets[(array[j] - min)/bucketRangeIncrease].push_back(array[j]);
    307     }
    308     array.clear();
    309     for (int k = 0; k < bucketCount; ++k) {
    310         if (buckets[k].empty()) {
    311             continue;
    312         }
    313         InsertionSort1(buckets[k]);
    314         for (int i = 0; i < buckets[k].size(); ++i) {
    315             array.push_back(buckets[k][i]);
    316         }
    317     }
    318 }
    319 
    320 void RadixSort(std::vector<int> &array) {
    321     const size_t sz = array.size();
    322     if (sz <= 1) {
    323         return;
    324     }
    325     int max = std::numeric_limits<int>::min();
    326     for (int i = 0; i < sz; ++i) {
    327         if (max < array[i]) {
    328             max = array[i];
    329         }
    330     }
    331     int count = 1;
    332     int radix = 1;
    333     while (max / radix > 10) {
    334         radix *= 10;
    335         count++;
    336     }
    337     std::vector<std::vector<int>> buckets;
    338     for (int j = 1; j <= count; ++j) {
    339         buckets.clear();
    340         buckets.resize(10); // 0 - 9
    341         radix = 1;
    342         for (int k = 1; k < j; ++k) {
    343             radix *= 10;
    344         }
    345         for (int i = 0; i < sz; ++i) {
    346             int index = (array[i] / radix) % 10;
    347             buckets[index].push_back(array[i]);
    348         }
    349         array.clear();
    350         array.reserve(sz);
    351         for (int l = 0; l < 10; ++l) {
    352             for (int i = 0; i < buckets[l].size(); ++i) {
    353                 array.push_back(buckets[l][i]);
    354             }
    355         }
    356     }
    357 }
  • 相关阅读:
    使用BigQuery分析GitHub上的C#代码
    ASP.NET Core 处理 404 Not Found
    C# 7 局部函数剖析
    调试 ASP.NET Core 2.0 源代码
    Entity Framework Core Like 查询揭秘
    ASP.NET Core Razor 视图组件
    Thread 1 cannot allocate new log引起的宕机事故(转载)
    docker默认网段和主机网段冲突解决
    docker安装异常以及网络问题总结
    max virtual memory areas vm.max_map_count [65530] is too low, increase to at least [262144]
  • 原文地址:https://www.cnblogs.com/hgwang/p/15155507.html
Copyright © 2011-2022 走看看