数据结构

(ง •_•)ง今天肚子里没有墨水了,我去喝点墨,明天和大家聊一聊呀!o( ̄︶ ̄)o

给大家推荐一首歌 “Por una Cabeza”,
听上去蛮浪漫的,很有风味。

这首歌,我是从《辛德勒名单》开头听到的,不得不说电影制作人独具匠心,极力渲染德国军官聚餐时的欢娱,却在字里行间暗示着犹太人即将面临的一场厄运,大家有机会可以去看看、温习温习。

1.排序算法

(1)快速排序

快速排序法,排序速度的真的很快嘛?可能只是稍微提高一点点,毕竟无序到有序时非自发的,熵值要改变很多ヾ(^ ▽^*)))。
快速排序大体的思路就是,你选择原来无序序列中的某一个元素,然后使得在他前面的元素都比他小,在他后面的元素位置都比他大。(注意序列的总长度不变,所以只能交换序列中在不同位置元素的值)

大家不妨想一下,这个数前面的数都比他小,后面数都比他大,这个数位置不就排好了嘛?只不过在他前面和在他后面的数可能位置还有待商榷,所以一次快速排序的操作完成后,按理说至少有一个元素的位置已经排好了。

要使快速排序更有效的话,肯定是数值大小在中值附近的元素比较好了,这样子的话,我们初始选定的数就是在 ( A [ 0 ] , A [ N − 1 ] , A [ N − 1 2 ] ) (A[0],A[N-1],A[\frac{N-1}{2}]) (A[0],A[N1],A[2N1])中选择中值,然后开始操作,这样就相当于把原来的表分成了两块了,比初始选定数大的和比初始数小的。

然后以这个数的位置分别为新的上下边界,继续分割,这样不断分,最后肯定会分成一段子表中只有2个或者1个元素,那么我们就完成排序了。

其中,优化部分是,当子表分得很小了的时候,快速排序与冒泡排序的时间复杂度相差不大,所以在字表小的时候,用冒泡排序优化函数

快速排序代码如下:

int mid(int a[],int,int);     //三个数求中间值
void bubsort(int a[],int,int);    //双向冒泡排序法
int split(int a[],int,int);     //快速排序法——分割原序列
void qksort(int a[],int,int);    //快速排序递归调用

//所有的m是数组下限,n是数组上限

void qksort(int a[],int m,int n)  
{
	 int i;
	 if(n-m>mid(a,m,n))      //快速排序优化
 	{
  	i=split(a,m,n);      //数量大
  	qksort(a,m,i-1);     //快速排序
  	qksort(a,i,n);
 	}
 	else         //数量较小时
  	bubsort(a,m,n);      //采取冒泡排序
}

int split(int a[],int m,int n)
{
 	int i,j,t,k;
 	k=mid(a,m,n);       //寻找合适大小的数
 	t=a[k];
 	a[k]=a[m];
 	i=m;
 	j=n;
 	while(i!=j)        //分割表格
	 {
  		while(a[j]>=t && i<j) j--;
  		if(i<j)
 		 {
  		 	a[i]=a[j];
  			 i++;
   			while(a[i]<=t && i<j) 
   				 i++;
  			 if(i<j) 
			    {a[j]=a[i];j=j-1;}
		  }
	 }
	 a[i]=t;
	 return i;
}
void bubsort(int a[],int m,int n)
{ 
	 int k,i,j,t,s;
	 s=n;
	 k=m;
 	while(k<s)
 	{
		  j=s;
		  s=0;
	  	for(i=k;i<j;i++)      //顺序冒泡排序
  		{
  			 if(a[i]>a[i+1])
 			  {t=a[i];a[i]=a[i+1];a[i+1]=t;s=i;}
		}
		if(s==0) break;
  		j=k+1;
  		k=0;
  		for(i=s-1;i>-1;i--)      //逆序冒泡排序
  		{
   			if(a[i-1]>a[i]) 
   			{t=a[i];a[i]=a[i-1];a[i-1]=t;k=i;}
  		}
  		if(k==0) break;
 	}
}
int mid(int a[],int m,int n)     //寻找中值
{
 	if((a[m]-a[n])*(a[m]-a[(m+n)/2])<0)
 	return a[m];
 	else
	{ 
 		if((a[n]-a[m])*(a[n]-a[(m+n)/2])<0)
   		return a[n];
  		else
   		return a[(m+n)/2];
	}
}

在主函数中调用格式如下

#include<stdio.h>
#include<stdlib.h>
#include<time.h>
#define N 100

void print(int a[],int);     //输出数组序列

void main()
{
	int i,j=0,a[N];
	srand((unsigned)time(NULL));
	 for(i=0;i<N;i++)
 	{
 		 a[i]=(int)(rand())%1000;   //创建随机数组
  	 }
	printf("原数组输出:\n");
	print(a,N);
	qksort(a,0,N-1);
	printf("快速排序:\n");
 	print(a,N);
}

void print(int a[],int n)
{
 	int i;
	for(i=0;i<n;)
 	{
  		printf("%5d",a[i]); 
  		i++;
  		if(i%10==0)
   		printf("\n");
 	}
 	printf("\n");
}

可能一天讲一个,这样循序渐进比较好,一下子讲太多,我的CPU可能要烧掉(昨天晚上不断的试错),所以大家如果对快速排序还有问题的话,可以评论戳我哦,下面?的几个我在五一假期里面和大家分享呀!

( o=^•ェ•)o ┏━┓最近迷上颜文字。。。。

(2)希尔排序——敬请期待

U•ェ•*U

(3)堆排序——敬请期待

O(∩_∩)O

2.查找算法——对分查找(敬请期待)

<( ̄︶ ̄)↗[GO!]

3.二叉树算法——二叉排序树(敬请期待)

~_~ ^0^
  • 3
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值