问题描述:给出一个数值,在给定的一个数组中快速定位该值的具体位置
前提条件:数组必须是已经排好顺序的,否则该算法不能达到预期的效果
实现步骤:由于数组是顺序排列的,所以可以采用一刀切的方式。
步骤1:取数组的中间位置,在该位置左侧的数值都比该位置上的数值要大(小),在该值右侧位置上的数值都比它的数值要小(大)。
步骤2:将中间位置上的值和目标值进行比较,若相等,则该位置就是我们所需的位置;若不等,就可以把搜索区间缩小到中间位置的左侧部分或者右侧部分,重复执行步骤1(注意:此时的中间位置对应的是缩小后的左侧区间或右侧区间)。
递归方式实现代码如下:
//在有序的数组里使用二分法查找某个数,并返回该数的下标,未找到则返回-1
public int binary(int[] sortArry,int target,int left,int right)
{
int index = -1;
//异常情况的处理,同时包含递归调用的终止条件
if(sortArry == null || left-right>0 || right<0)
return index;
int mid = (left+right)/2;
if(sortArry[mid] == target)
{
index = mid ;
return index;
}
else if(sortArry[mid]>target)
{
return binary(sortArry,target,left,mid-1);
}
else {
return binary(sortArry,target,mid+1,right);
}
}
非递归方式实现代码如下:
public int binary2(int[] sortArry, int target)
{
int index = -1;
if(sortArry == null)
return index;
int left =0;
int right = sortArry.length-1;
int mid;
while(left<=right)
{
mid=(left+right)/2;
if(sortArry[mid] == target ) {
index = mid;
//找到目标值后需要立刻返回,否则该循环会一直进行下去
return index;
}
else if(sortArry[mid] > target )
{
right=mid-1;
}
else left=mid+1;
}
return index;
}
需要注意的是,无论递归还是非递归的实现方式,都需要添加一个用于终止递归(递循环)的条件判断,否则会出现无限递归(无线循环),造成堆栈溢出而报错。