目录
冒泡排序
#include <iostream>
using namespace std;
void maopao(int* a, int n)
{
bool exchange = true;
int i = 1;
while (exchange) //如果没改变就直接退出循环,因为已经排好了
{
exchange = false;
for (int j = 0; j < n-i; j++)
{
if (a[j] > a[j + 1]) {
int temp = a[j];
a[j] = a[j + 1];
a[j + 1] = temp;
exchange = true;
}
}
i++;
}
}
int main() {
int a[5] = { 80,50,47,12,50 };
maopao(a, 5);
for (int i = 0; i < 5; i++) {
cout << a[i] << " ";
}
}
折半插入排序
1.介绍
折半插入是指,插入时使用折半算法来进行,一般的比如数组a[1,2,3,5,6,4]已经进行到了4了,low=0,high=4,就用折半算法,计算第一次插入位置为mid=(0+4)/2=2,比4小,插入右边,low=mid+1=3,high=4第二次插入的位置mid=(3+4)/2=3,比4大,插入左边 low=3,high=mid-1=2,high<low,退出循环,low右边包括low位置的右移一格,把4放入a[low]位置
#include <iostream>
using namespace std;
void charu(int* a, int n)
{
for (int i = 1; i < n; i++)
{
int temp = a[i];
int low = 0, high = i - 1;
while (low <= high) {
int mid = (low + high) / 2;
if (temp < a[mid]) {
high = mid - 1;
}
else
low = mid + 1;
}
for (int j = i - 1; j >= low; j--)
{
a[j + 1] = a[j];
}
a[low] = temp;
}
}
int main() {
int a[5] = { 50,40,20,60,80 };
charu(a, 5);
for (int i = 0; i < 5; i++) {
cout << a[i] << " ";
}
}
希尔排序
希尔是通过插入排序来改进的
#include <iostream>
using namespace std;
void xier(int* a, int n) {
for (int d = n / 2; d >= 1; d = d / 2) { //每隔d-1个为一个组
for (int i = d; i < n; i++) { //从第一组的第二个开始排序
int j = i - d;
int temp = a[i];
for (j ; j >= 0 && temp < a[j]; j = j - d) { //只有temp比前面的小才会继续执行下去,如果执行到了越界说明前面的都比temp大,
a[j + d] = a[j]; //比temp大的元素后移
}
a[j + d] = temp; //因为for循环中有j=j-d;所以最后还会-d,所以要+d
}
}
}
int main() {
int a[5] = { 50,40,2090,4,505 };
xier(a, 5);
for (int i = 0; i < 5; i++) {
cout << a[i] << " ";
}
}
快速排序
#include <iostream>
using namespace std;
int Partition(int* A, int low, int high) {
int Pivot = A[low];
while (low < high) { //比Pivot大的在右边,小的在左边
while (low < high && A[high] >= Pivot) high--;
A[low] = A[high];
while (low < high && A[low] < Pivot) low++;
A[high] = A[low];
}
A[low] = Pivot;
return low;
}
void QuickSort(int* A, int low, int high) {
if (low < high)
{
int pivotpos = Partition(A, low, high); //左边比pivotpos小,右边比pivotpos大,所以分开继续用快速排序
QuickSort(A, low, pivotpos - 1);
QuickSort(A, pivotpos + 1, high);
}
}
void Print(int A[],int n) { //输出函数
for (int i = 0; i < n; i++) {
cout << A[i] << " ";
}
}
int main() {
int A[5] = { 50,10,20,30,8};
Print(A, 5);
cout << endl;
QuickSort(A, 0, 4);
Print(A, 5);
}
堆排序
#include <iostream>
using namespace std;
//处理的是大根堆 a[0]不是堆元素
void Sifi(int* a, int k, int n) { //k为待处理的元素序号,n为总元素
int i = k; //待处理元素编号
int j = 2 * i; //左孩子
//if (k == 0) { //如果为根,左孩子为1
// j = 1;
//}
while (j <= n) //左孩子存在才能执行 左孩子存在右孩子才有可能存在
{
if (j < n) {
if ( a[j] < a[j + 1]) //如果有右孩子,而且右孩子比左孩子大,则j指向右孩子
j++;
}
if (a[i] < a[j]) //如果待处理元素比孩子小,则下坠
{
int temp = a[i];
a[i] = a[j];
a[j] = temp;
i = j; //待处理元素下坠到j 继续判断是否需要下坠
j = 2 * i; //下坠后的元素的左孩子的编号
}
else
break;
}
}
void HeapSort(int* a, int n) {
for (int i = n / 2; i >= 1;i--) { //建立堆,从最后一个的非终端结点至根结点进行下坠
Sifi(a, i, n);
}
for (int i = 1; i < n; i++) { //只需要执行n-1次就可以把堆排序成功
int temp = a[1]; //将最大的堆顶元素与最后一个元素互换
a[1] = a[n - i + 1];
a[n - i + 1] = temp;
Sifi(a, 1, n - i); //让堆顶下坠
}
}
int main() {
int a[9] = {0,36,30,18,40,32,45,22,50}; //a[0]不能算入堆中 n代表有效元素
HeapSort(a, 8);
for (int i = 0; i < 9; i++)
{
cout << a[i] << " ";
}
}
归并排序(递归)
#include <iostream>
using namespace std;
void Merge(int* a, int* b, int low, int mid, int high) { //a[low]到a[mid]和a[mid+1]到a[high]为两个有序序列,将其复制到b再合并回a中
int i = low; //a前半部分的头 //将a复制到b的步骤在MergeSort2函数中
int j = mid+1; //a后半部分的头
int k = low; //b前半部分的头,加入数组
for (int p = low; p <= high; p++) { //b数组需要实时更新
b[p] = a[p];
}
while (i <= mid && j <= high) { //如果前半段的大则加入数组
if (b[i] <= b[j]) {
a[k] = b[i];
k++;
i++;
}
else
{
a[k] = b[j]; //如果后半段大则加入数组
k++;
j++;
}
} //多余的部分肯定是比前面的大所以可以直接加入
while (i <= mid) { //如果前半段有多余的部分加入数组中
a[k] = b[i];
k++;
i++;
}
while (j <= high) { //如果后半段有多余数组加入数组中
a[k] = b[j];
k++;
j++;
}
}
void MergeSort2(int* a, int* b, int low, int high) {
//if (low == high) { //这个b数组需要和a数组实时更新
// b[low] = a[low];
//}
if(low<high) {
int mid = (low + high) / 2;
MergeSort2(a, b, low, mid); //归并前半部分0-3,0-1,4-5
MergeSort2(a, b, mid + 1, high); //归并后半部分4-7,2-3,6-7
Merge(a, b, low, mid, high); //归并0-1和2-3,,归并4-5和6-7,归并0-3和4-7
}
}
int main() {
int a[8] = { 50,10,50,20,30,40,90,80 };
int b[8];
MergeSort2(a, b, 0, 7);
for (int i = 0; i < 8; i++)
{
cout << a[i] << " ";
}
cout << endl;
for (int i = 0; i < 8; i++) //b为最后一遍的归并排序之前的状态
{
cout << b[i] << " ";
}
}
基数排序