超全经典排序大汇总
算法思想
每一趟在待排元素中选取关键字最小的元素加入到有序序列
注:
简单选择排序与序列的初始状态无关,仅与序列的元素个数有关
时间复杂度
- 最好 — $O(n^2)$
- 最坏 — $O(n^2)$
- 平均 — $O(n^2)$
演示动画
空间复杂度
仅用一个临时变量 min — $O(1)$
稳定性
不稳定
适用性
- 顺序表
- 链表
算法特点
- 不稳定,但改变策略可以写出不产生“不稳定现象”的选择排序算法
- 可用于链式存储结构
- 移动次数较少,当每一记录占用的空间较多时,此方法比直接插入排序快
- 选择排序的主要操作是关键字的比较,因此,改进此算法应从减少“比较次数”出发考虑
核心代码
//交换两个元素
void swap(int &a, int &b){
int temp = a;
a = b;
b = temp;
}
//选择排序
void SelectSort(int a[], int n){
for(int i = 0; i < n; i ++){
int min = i;//min记录最下元素的下标
for(int j = i; j < n; j ++){
if(a[j] < a[min]) min = j;
}
if(min != i) swap(a[i], a[min]);//交换两个值
}
}
完整代码
#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <fstream>
using namespace std;
const int N = 20;
int num;
int data[N],idx;
//交换两个元素
void swap(int &a, int &b){
int temp = a;
a = b;
b = temp;
}
//选择排序
void SelectSort(int a[], int n){
for(int i = 0; i < n; i ++){
int min = i;//min记录最下元素的下标
for(int j = i; j < n; j ++){
if(a[j] < a[min]) min = j;
}
if(min != i) swap(a[i], a[min]);//交换两个值
}
}
int main(){
//打开文件
ifstream infile;
infile.open("D:\\学习\\数据结构\\第8章排序\\in.txt", ios::in);
//写文件
ofstream outfile;
outfile.open("D:\\学习\\数据结构\\第8章排序\\out.txt", ios::out);
if(!infile.is_open()){//判断文件打开是否成功
cout << "file open failure!" << endl;
}
infile >> num;//读取元素个数
while(num --){//将文件中的元素复制到data[1...n] 数组中
infile >> data[idx ++];
}
cout << "排序前元素序列:" << endl;
for(int i = 0; i < idx; i ++) cout << data[i] << ' '; cout << endl;
cout << "使用sort函数排序后序列: " << endl;
sort(data, data + idx);
for(int i = 0; i < idx; i ++) cout << data[i] << ' '; cout << endl;
SelectSort(data, idx);
cout << "使用选择排序后序列为:" << endl;
for(int i = 0; i < idx; i ++) cout << data[i] << ' '; cout << endl;
num = idx, idx = 0, outfile << num << endl;//写入数据数num以及在行末写入\n
while(num --){
outfile << data[++ idx] << ' ';//将排序后的数据写到文件中
}
outfile << endl;//向文件末尾写入\n结束符
//关闭文件
infile.close();
outfile.close();
return 0;
}
输入数据(in.txt)
10
13 69 86 99 59 23 64 32 86 72
输出数据(out.txt)
10
13 23 32 59 64 69 72 86 86 99