Sort 排序类-1 基本排序

排序的一些概念

  排序的稳定性:
    如果在序列中有两个数据元素 r[i] 和 r[j],它们的关键字 k[i]== k[j],且在排序之前,对象 r[i] 排在 r[j] 前面;
    如果在排序之后,对象 r[i]仍在对象 r[j] 的前面,则称这个排序方法是稳定的,否则称这个排序方法是不稳定的。

稳定性排序示例

  排序的重要指标:
    排序的时间复杂度
    排序的空间复杂度
    排序算法的可读性与可维护性

  多关键字与单关键字的排序无本质区别,只是在第一关键字相同时,再去比较第二关键字继续排序,以此类推。

  tip:
    Sort类中都提供了Asc(bool类型)变量,可以选择(true)升序或降序(false)排序。默认为升序
    因为待排序的对象不一定为基本类型,所以使用模板技术,可以对支持比较与交换的数据对象进行排序。
    下面是交换函数(模板)。

	template < typename T >
	static void swap(T& a,T& b)
	{
		T c(a);
		a = b;
		b = c;
	}

选择排序

  选择排序的基本思想:
    每次(例如第i次,i=0,1,…,n-2)从后面的n-i个待排数据元素中
    选出最小(大)的元素,作为排序后的第i个元素

不多说,选择排序看代码应该就可以理解了,不理解就多看两遍。

	/*				选择排序 O(n2)
	不稳定排序
	*/
	template < typename T >
	static void Select(T arr[],int len,bool ASC = true)
	{
		for(int i=0;i<len;i++)
		{
			int spe = i;
			for(int j=i+1;j<len;j++)//找出最小的值
			{
				if(ASC ? (arr[spe] > arr[j]) : (arr[spe] < arr[j]) )
				{
					spe = j;
				}
			}
			if(spe != i)
			{
				swap(arr[spe],arr[i]);
			}
		}
	}

插入排序

  插入排序的基本思想:
    当插入第i(i>=1)个数据元素时,前面的V[0],V[1],…'V[i-1]已经排好序;
    这时,用V[i]的关键字与V[i-1],V[i-2],…,V[0]的关键字进行比较,
    找到位置后将V[i]插入,原来位置上的对象向后顺移。

  流程简述:
    0:(外围大循环 0-n)
    1:拷贝当前待排序数据(待排序数据顺序为从前向后),向前比较
    2:若比较成立(逆序),当前被比较数据向后顺移一位,记录当前下标,向前比较,重复2
    3:若比较不成立,记录的下标与待排序数据的下标是否一致
    4:不一致,将待排序数据插入至此
    5:一致,不需要操作

	/*				插入排序 O(n2)
	稳定排序
	*/
	template < typename T >
	static void Insert(T arr[],int len,bool ASC = true)
	{
		for(int i=1;i<len;i++)
		{
			int spe = i;
			T e = arr[i];
			for(int j=i-1;(j>=0)&&(ASC ? (e < arr[j]) : (e > arr[j]) );j--)
			{
				arr[j+1] =  arr[j];
				spe = j;
			}
			if(spe != i)
			{
				arr[spe] = e;
			}
		}
	}

冒泡排序

  冒泡排序的基本思想:
    每次从后向前进行(假设第i次),j=n-1,n-2,…,i,
    两两比较V[j-1]和V[j]的关键字;
     如果发生逆序,则交换V[j-1]和V[j]

  流程简述:
    0:(外围大循环 0-n)
    1:当前待排序数据(待排序数据顺序为从后向前)向前比较
    2:若比较成立(逆序),当前被比较数据与待排序数据交换位置
    3:若比较不成立,不需要操作
    4:重复1

  tip:
    采用Exchange(bool类型)标记当前排序数据是否发生位置移动,如果没发生,说明数据已经排好序,可以提前结束排序操作,提高效率

	/*				冒泡排序 O(n2)
	稳定排序
	*/
	template < typename T >
	static void Bubble(T arr[],int len,bool ASC = true)
	{
		bool exchange = true;
		for(int i=0;(i<len) && exchange;i++)
		{
			exchange = false;
			for(int j=len-1;j>i;j--)//找出最小的值
			{
				if(ASC ? (arr[j] < arr[j-1]) : (arr[j] > arr[j-1]) )
				{
					swap(arr[j],arr[j-1]);
					exchange = true;
				}
			}
		}
	}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值