数据结构(11)_排序
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了数据结构(11)_排序相关的知识,希望对你有一定的参考价值。
1.排序的基本概念
1.1.排序的概念
定义:排序是计算机内经常进行的一种操作,其目的是将一组“无序”的数据调整为“有序”的数据元素。
数学定义:假设含有n个数据元素的序列为{R1,R2...Rn},其相应的关键字序列为:{K1,K2...Kn};这些关键字相互之间进行比较,即:在他们之间存在着这样的一个关系:Kp1 <= Kp2 <= ... <= Kpn按此固有关系将上式重新排列为:{Rp1, Rp2, ... Rpn}的操作称为排序。
1.2.排序的稳定性
问题:什么按照总评排序后张无忌的排名比郭靖靠前呢?
排序的稳定性:
如果序列中有两个数据元素Ri和Rj,他们关键字的Ki == Kj,且排序之前,对象Ri排在Rj之前,但排序之后两者的顺序交互,则称这个排序方案是不稳定的。
1.3.多关键字排序
排序时需要比较的关键字有多个,排序结果首先按照关键字1进行,当关键字1相同,按照关键字2进行排序...
多关键字的排序并不比单关键字复杂,只需要在定义比较操作时,同时考虑多个关键字即可!
多关键字排序实例:
class MulitKeySort : public Object
{
protected:
int key1;
int key2;
public:
MulitKeySort(int k1, int k2)
{
key1 = k1;
key2 = k2;
}
bool operator ==(const MulitKeySort& m)
{
return ( (key1==m.key1) && (key2==m.key2));
}
bool operator !=(const MulitKeySort& m)
{
return !(*this == m);
}
bool operator <(const MulitKeySort& m)
{
return ( (key1<m.key1) || ((key1==m.key1) && (key2<m.key2)));
}
bool operator >=(const MulitKeySort& m)
{
return !(*this < m);
}
bool operator >(const MulitKeySort& m)
{
return ( (key1>m.key1) || ((key1==m.key1) && (key2>m.key2)));
}
bool operator <=(const MulitKeySort& m)
{
return !(*this > m);
}
};
//测试代码:
void test_1()
{
MulitKeySort m1(3, 4);
MulitKeySort m2(3, 3);
cout << (m1 > m2) << endl;
}
1.4.排序的选择
排序中的关键操作
- 比较:任意两个数据元素通过比较操作确定先后次序。
- 交换:数据元素之间需要交换才能得到预期的结果。
排序的选择依据: - 时间性能,关键性能差异体现在比较和交换的数量
- 辅助存储空间:完成排序操作需要额外的存储空间,必要时可以“空间换时间”
-
算法的实现复杂度:过于复杂的排序算法可能影响可读性和可维护性。
1.5.排序类的设计
继承自顶层父类Object,并且私有化所有构造途径,将各种排序算法设计为静态成员函数。
class DTSort : public Object { private: DTSort(); DTSort(const DTSort&); DTSort& operator =(const DTSort&); template < typename T > static void Swap(T& a, T& b) { T c(a); a = b; b = c; } };
2.选择排序与插入排序
2.1.选择排序
基本思想:每次(例如第i次,i=0,1,2...,n-2)从后面n-1个待排列的的数据元素中选出关键字最新的元素,左右有序元素序列的i个元素。
template < typename T > static void SelectSort(T array[], int len, bool min2max = true) { for(int i=0; i<len; i++) { int min = i; for(int j=i+1; j<len; j++) { if(min2max ? array[j]<array[min] : array[j]>array[min]) { min = j; } } if(i != min) { Swap(array[i], array[min]); } } }
2.2.插入排序
当插入第i(i>=1)个数据元素时,前面的V[0],V[1],...,V[i-1]已经排好序,这时用V[i]的关键字与前i-1个关键字进行比较,找到位置后将V[i]插入,原来位置上的对象向后顺移。
template < typename T > static void InsertSort(T array[], int len, bool min2max = true) { for(int i=1; i<len; i++) { int k = i; T e = array[i]; for(int j=i-1; (j>=0) && (min2max ? array[j]>e : array[j]<e); j--) { array[j+1] = array[j]; k = j; } if(k != i) { array[k] = e; } } }
总结:
1.选择排序每次选择未排序的最小元素,插入排序每次将第i个元素插入前面i-1个已经排序的序列;
2.选择排序是不稳定的排序法,插入排序时稳定的排序法。两者的时间复杂度都未O(n^2)
以上是关于数据结构(11)_排序的主要内容,如果未能解决你的问题,请参考以下文章
初识Spring源码 -- doResolveDependency | findAutowireCandidates | @Order@Priority调用排序 | @Autowired注入(代码片段
初识Spring源码 -- doResolveDependency | findAutowireCandidates | @Order@Priority调用排序 | @Autowired注入(代码片段