博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
折半查找插入排序法
阅读量:7204 次
发布时间:2019-06-29

本文共 2738 字,大约阅读时间需要 9 分钟。

我们知道折半查找只能在有序的数组里才能使用。

其实在插入排序过程中,大家细心的话会发现,每次找插入位置时,这段元素是有序的,那么在这里为使用折半查找提供了条件。

 但是用传统的折半查找肯定不行,因为我们这里要找的是要插入的位置

例如:42,53, 64, 85, 58这5个元素在插入排序里就是58前面的元素全部有序,我们要找的是58应该插入的位置,应该是在64所在的位置

而这个64所在的位置就是我们折半查找要查找的位置,其实就是53<58<64,在这里我对折半查找稍作改进

int binsearch(int *A,int first,int last,int x){	int mid=0;	int a=0;	while(first>=0&&last>=0&&(last-first)>1)	{		mid=(first+last)/2;		a=COMPARE(A[mid],x);		switch(a)		{		case 1:		last=mid;    break;                  //在这里对折半查找稍作改动last=mid-1;改为last=mid;		case 0:		return mid;    break;		case -1:	first=mid;   break;                  //这里也对折半查找稍作改动		}	}	mid=(first+last)/2;	if((COMPARE(A[mid],x)==1)&&mid==0)                   //当插入位置w为A[0]时,要另外讨论		return 0;	else                                                 		return last;}

首先last=mid-1;改为last=mid;     first=mid+1;也改为了first=mid;循环退出条件改为while(first>=0&&last>=0&&(last-first)>1)

如此一来,我们最终总会得到上面示例中first位于53所在的位置,last位于64所在的位置,一般情况下我们只要返回last就够了

但有一种情况要注意,就是当要查找的位置位于元素最前面,例如:42,56,78,98,31

如果按照上述方法,first位于42所在的位置,last位于56所在的位置,如果此时返回last肯定是不对的。

所以对于这种情况,要另外讨论mid=(first+last)/2;  if((COMPARE(A[mid],x)==1)&&mid==0)    return 0;

再一次取mid,如果mid==0;说明first位于42所在的位置,last位于56所在的位置,而且if(COMPARE(A[mid],x)==1),如果A[mid]>x,即42>31,那么这时该插入的位置应该位于A[0]

以下是折半插入排序部分代码:

void Insertionsort2(int *A,int n){	int i=0;	int j=0;	int v=0;		for(i=1;i
v) { j=binsearch(A,0,i-1,v); //用折半查找找到要插入的位置 for(;i>j;i--) { A[i]=A[i-1]; } A[j]=v; } }}

下面是我的测试代码,已测试过

//折半插入排序Insertsort2()#include 
#include
#include
#define COMPARE(x,y) (((x)>(y))?1:(((x)==(y))?0:-1))void print(int *A,int n);void Insertionsort2(int *A,int n);int binsearch(int *A,int first,int last,int x);void main(){ int n=0; int i=0; //循环变量 int *A=NULL; printf("你想要多少个随机数? "); scanf("%d",&n); if(n<1) n=1; A=(int*)malloc(n*sizeof(int)); if(A==NULL) { printf("Out of memory!\n"); exit(1); } srand(time(NULL)); //产生0~999之间的n个随机数 for(i=0;i
v) { j=binsearch(A,0,i-1,v); //用折半查找找到要插入的位置 for(;i>j;i--) { A[i]=A[i-1]; } A[j]=v; } }} void print(int *A,int n){ int i=0; for(i=0;i
=0&&last>=0&&(last-first)>1) { mid=(first+last)/2; a=COMPARE(A[mid],x); switch(a) { case 1: last=mid; break; //在这里对折半查找稍作改动last=mid-1;改为last=mid; case 0: return mid; break; case -1: first=mid; break; //这里也对折半查找稍作改动 } } mid=(first+last)/2; if((COMPARE(A[mid],x)==1)&&mid==0) //当插入位置w为A[0]时,要另外讨论 return 0; else return last;}

对于算法方面的问题,确实不容易想,为这个问题我也苦恼了很长时间,发了帖子也没有有价值的回复,甚至有人嘲讽你,但我最终还是做出来了

这个算法可能不是很好,但是这真是我自己想出来的,完全原创。

大家有什么别的思路完全可以交流交流,呵呵O(∩_∩)O~

转载地址:http://sydum.baihongyu.com/

你可能感兴趣的文章
【LeetCode】93. Restore IP Addresses
查看>>
2014 百度之星题解 1002 - Disk Schedule
查看>>
Kernel数据结构移植(list和rbtree)
查看>>
ngnix编译遇到的问题.
查看>>
关于 ioctl 的 FIONREAD 參数
查看>>
Ubuntu Linux下如何配置Android开发环境
查看>>
ASP.NET的一套笔试题
查看>>
Remove Nth Node From End of List leetcode java
查看>>
这是一张很有趣的图片, 通常女性会先看到月亮, 男性会先看到人脸. 如果相反, 表示你体内的异性荷尔蒙偏高哦!...
查看>>
SGU 403 Game with points
查看>>
2014中国软件开发者调查(一):Java最受欢迎 第二语言JS使用比例最高
查看>>
三级管的原理
查看>>
Java基础—ClassLoader的理解
查看>>
Android App监听软键盘按键的三种方式(转)
查看>>
2、Android应用程序基本特性
查看>>
Android开发之Buidler模式初探结合AlertDialog.Builder解说
查看>>
bash shell命令(2)
查看>>
html中#include file的使用方法
查看>>
eclipse: Program "g++" not found in PATH
查看>>
Python基础(11)--面向对象1
查看>>