java 实现:
// java 实现 二分查找,如果没查找到,显示离代查找值最近的值
// main
public static void main(String[] a) {
int[] array = {1, 3, 5, 7, 9, 11};
int findValue = 6;
int re = search(array, findValue);
System.out.println(re); // 打印: 没查找到 6。离代查找值最近的值是 : 5 和 7
int re2 = searchRecursive( array, findValue, 0, array.length - 1 );
System.out.println(re2);
}
// java 二分查找 --- while 实现
public static int search( int[] array, int findValue ){
// 查找次数
int count = 0;
// 代查找值 比 中值 大还是小
int lgOrlt = -1;
// 如果数组为空,直接返回 -1,即查找失败
if (array == null) {
return -1;
}
// 起始位置
int start = 0;
// 结束位置
int end = array.length - 1;
// 中间位置
int middleIndex = -1;
// 中值
int middleValue = 0;
while ( start <= end ) {
count ++;
middleIndex = ( start + end ) / 2;
middleValue = array[ middleIndex ];
if ( findValue == middleValue ) {
// 找到了
lgOrlt = 0;
// 等于中值,直接返回
return middleIndex;
} else if ( findValue < middleValue ) {
// 小于中值时,在中值前面找
lgOrlt = 1;
end = middleIndex - 1;
} else {
// 大于中值时,在中值后面找
lgOrlt = 2;
start = middleIndex + 1;
}
}
System.out.print( "没查找到 " + findValue + "。离代查找值最近的值是 : " );
if ( lgOrlt == 1 ){
// 小于中值时,在中值前面找
if ( middleIndex > 0 ) {
System.out.print( array[ middleIndex - 1 ] );
System.out.print( " 和 " );
System.out.print( middleValue );
System.out.println();
} else {
System.out.println( array[ 0 ] );
}
} else if ( lgOrlt == 2 ) {
// 大于中值时,在中值后面找
if ( middleIndex < array.length - 1 ){ // 注意这里要写 middleIndex < array.length - 1,不要写 middleIndex < end,因为 end 是动态变化的
System.out.print( middleValue );
System.out.print( " 和 " );
System.out.print( array[ middleIndex + 1 ] );
System.out.println();
} else {
System.out.println( array[ array.length - 1 ] );
}
}
// 返回 -1,即 没查找到
return -1;
}
// java 二分查找 递归实现
// 查找次数
private static int count = 0;
// 代查找值 比 中值 大还是小
private static int lgOrlt = -1;
// 中间位置
private static int middleIndex = -1;
// 中值
private static int middleValue = 0;
// 二分查找 --- 递归 实现
public static int searchRecursive( int[] array, int findValue,
int start, int end ){
// 如果数组为空,直接返回 -1,即没查找到
if (array == null) {
return -1;
}
count++;
if ( start <= end ){
middleIndex = ( start + end ) / 2;
middleValue = array[ middleIndex ];
if ( findValue == middleValue ){
lgOrlt = 0;
// 等于中值,直接返回
return middleIndex;
} else if ( findValue < middleValue ){
// 小于中值时,在中值前面找
lgOrlt = 1;
return searchRecursive( array, findValue, start, middleIndex - 1 );
} else {
// 大于中值时,在中值后面找
lgOrlt = 2;
return searchRecursive( array, findValue, middleIndex + 1, end );
}
} else {
System.out.print( "没查找到 " + findValue + "。离代查找值最近的值是 : " );
if ( lgOrlt == 1 ){
// 小于中值时,在中值前面找
if ( middleIndex > 0 ) {
System.out.print( array[ middleIndex - 1 ] );
System.out.print( " 和 " );
System.out.print( middleValue );
System.out.println();
} else {
System.out.println( array[ 0 ] );
}
} else if ( lgOrlt == 2 ) {
// 大于中值时,在中值后面找
if ( middleIndex < array.length - 1 ){
System.out.print( middleValue );
System.out.print( " 和 " );
System.out.print( array[ middleIndex + 1 ] );
System.out.println();
} else {
System.out.println( array[ array.length - 1 ] );
}
}
// 返回 -1,即没查找到
return -1;
}
}
cpp 实现:
#include <string>
using namespace std;
void print( string st ) {
cout << ">>>" << st << endl;
}
void print( int a ) {
cout << ">>>" << a << endl;
}
void println() {
cout << endl;
}
// 把整型数字转换成字符串
string intToStr( int a ) {
char str[100];
char str1[100];
memset( str, 0, 100 );
memset( str1, 0, 100 );
int c = 0;
int i;
while( 1 ) {
str[c] = ( a % 10 ) + '0'; // 模10得到最低位,+‘0’变成字符
c++;
a = a / 10; // 除以10去掉已求出的最后低位,再循环计算
if ( a == 0 ) {
break;
}
}
for( i = 0, c = c-1; c >= 0; i++, c-- ) {
str1[i] = str[c];
}
//print( str1 );
return str1;
}
// cpp 二分查找 --- while 实现
int search( int arrayLength, int array[], int findValue ) {
// 如果数组为空,直接返回 -1,即查找失败
if ( arrayLength == 0 ) { //cpp 判断数组为空
return -1;
}
// 起始位置
int start = 0;
// 结束位置
int end = arrayLength - 1;
// 中间位置
int middleIndex = -1;
// 中值
int middleValue = 0;
// 查找次数
int count = 0;
// 代查找值 比 中值 大还是小
int lgOrlt = -1;
while ( start <= end ) {
count ++;
middleIndex = ( start + end ) / 2;
middleValue = array[ middleIndex ];
//string st1 = " middleValue = " + intToStr( middleValue )
// + " middleindex = " + intToStr( middleIndex );
//print( st1 );
if ( findValue == middleValue ) {
// 找到了
lgOrlt = 0;
// 等于中值,直接返回
return middleIndex;
} else if ( findValue < middleValue ) {
// 小于中值时,在中值前面找
lgOrlt = 1;
end = middleIndex - 1;
//println( "小于中值时,在中值前面找 " );
} else {
// 大于中值时,在中值后面找
lgOrlt = 2;
start = middleIndex + 1;
//print( "大于中值时,在中值后面找 " );
}
}
//print( "查找次数 " + intToStr( count ) );
//print( "lgOrlt " + intToStr( lgOrlt ) );
//print( "middleIndex " + intToStr( middleIndex ) );
string st = "没查找到" + intToStr( findValue ) + " 离代查找值最近的值是 : ";
if ( lgOrlt == 1 ) {
// 小于中值时,在中值前面找
if ( middleIndex > 0 ) {
string temp = intToStr( array[ middleIndex - 1 ] ) + " 和 " + intToStr( middleValue );
st += temp;
print( st );
println();
} else {
print( array[ 0 ] );
}
} else if ( lgOrlt == 2 ) {
// 大于中值时,在中值后面找
if ( middleIndex < arrayLength - 1 ) {
string temp = intToStr( middleValue ) + " 和 " + intToStr( array[ middleIndex + 1 ] );
st += temp;
print( st );
println();
} else {
print( array[ arrayLength - 1 ] );
}
}
// 返回 -1,即 没查找到
return -1;
}
// cpp 二分查找 递归实现
// 查找次数
int count = 0;
// 代查找值 比 中值 大还是小
int lgOrlt = -1;
// 中间位置
int middleIndex = -1;
// 中值
int middleValue = 0;
// 二分查找 --- 递归 实现
int searchRecursive( int array[], int findValue, int start, int end ) {
// 如果数组为空,直接返回 -1,即没查找到
if ( sizeof( array ) == 0 ) {
return -1;
}
count++;
if ( start <= end ) {
middleIndex = ( start + end ) / 2;
middleValue = array[ middleIndex ];
if ( findValue == middleValue ) {
lgOrlt = 0;
// 等于中值,直接返回
return middleIndex;
} else if ( findValue < middleValue ) {
// 小于中值时,在中值前面找
lgOrlt = 1;
return searchRecursive( array, findValue, start, middleIndex - 1 );
} else {
// 大于中值时,在中值后面找
lgOrlt = 2;
return searchRecursive( array, findValue, middleIndex + 1, end );
}
} else {
string st = "没查找到";
st += intToStr( findValue );
st += " 离代查找值最近的值是 : ";
//print( "查找次数 " + count );
//print( "lgOrlt " + lgOrlt );
//print( "middleIndex " + middleIndex );
if ( lgOrlt == 1 ) {
// 小于中值时,在中值前面找
if ( middleIndex > 0 ) {
st += intToStr( array[ middleIndex - 1 ] );
st += " 和 ";
st += intToStr( middleValue );
print( st );
println();
} else {
print( array[ 0 ] );
}
} else if ( lgOrlt == 2 ) {
// 大于中值时,在中值后面找
if ( middleIndex < sizeof( array ) - 1 ) {
print( middleValue );
print( " 和 " );
print( array[ middleIndex + 1 ] );
println();
} else {
print( array[ sizeof( array ) - 1 ] );
}
}
// 返回 -1,即没查找到
return -1;
}
}
// main
void main() {
int array[] = { 1, 3, 5, 7, 9, 11 };
int findValue = 11;
int arrLength = sizeof( array ) / sizeof( array[0] );
// cpp 数组作为函数参数时,需要传递进去一个数组长度 arrLength,因为 cpp 不会在方法里辨别出数组的长度
int re = search( arrLength, array, findValue );
print( re );
int re2 = searchRecursive( array, findValue, 0, arrLength - 1 );
print( re2 );
}
// --- cpp 语法注意事项 ---
// int array[] --- cpp 数组是这样声明的
// cpp 数组作为函数参数时,需要传递进去一个数组长度 arrLength,因为 cpp 不会在方法里辨别出数组的长度
// 把整型数字转换成字符串,用 itoa,或者使用自己定制的函数
// cpp 类似 js,被调用的函数,需要在调用它的位置前面,进行声明
// 在函数外部调用 print( sizeof( array ) ); 打印的是数组所占的全部字节数,所以,可以在函数外部使用 sizeof( array ) / sizeof( array[0] ) 来计算数组的长度
// 如果函数有一个参数是数组,在函数内部调用 print( sizeof( array ) ); 打印的是数组第一个元素所占的字节数
// 要在 cpp 程序里使用 string,需要在文件头部这样引用 #include <string>
python 实现:
# py 二分法查找,递归实现。 还没实现没查找到时,显示离代查找值最近的值
def search_data(data,data_find): #
# 中间值的索引号的定义:数组长度/2
mid = int( len(data) / 2 )
# 判断从1开始的数字数组内查找
if data[mid] >= 1:
# 如果我们要找的值(data_find)比中间值(data[mid])小
if data[mid] > data_find:
print("要找的数比中间值[%s]小" % data[mid])
# 在中间值(data[mid])的左侧继续查找,在此函数中继续循环
search_data(data[:mid], data_find)
# 如果我们要找的值(data_find)比中间值(data[mid])大
elif data[mid] < data_find:
print("要找的数比中间值[%s]大" % data[mid])
# 在中间值(data[mid])的右侧继续查找,在此函数中继续循环
search_data(data[mid:], data_find)
else:
# 就是它
print("这就是要找的值[%s]" % data[mid])
else:
print("没找到")
#
if __name__ == '__main__': #
# 创建一个1到60万的连续数组
data = list( range(600000) )
# 调用函数找到等于 95936 的值
search_data( data, 95936 )
#
php 实现:
<?php
// binSearch.php
/*
递归 实现二分法查找
$search 函数 $array 为数组,$toSearch 为要找的值
$low 是数组第一个元素的索引
$high 数组最后一个元素的索引
*/
function searchRecursive( $array, $toSearch, $low = 0, $high = 0 ) {
// 判断数组元素的数量
if ( count( $array ) != 0 and $high == 0 ) { // 判断是否为第一次调用
// 数组的元素个数
$high = count( $array );
}
if ( $low <= $high ) { // 如果还存在剩余的数组元素
$mid = intval( ( $low + $high ) / 2 ); // 取 $low 与 $high 的中间值
//return $array[ $mid ];
if ( $array[ $mid ] == $toSearch ) {
return $mid; //如果找到则返回
} elseif ( $toSearch < $array[ $mid ] ) {
//如果上面没有找到,则继续查找
return searchRecursive( $array, $toSearch, $low, $mid - 1 );
} else {
return searchRecursive( $array, $toSearch, $mid + 1, $high );
}
}
return "没查找到输入的值";
}
/*
while 循环实现二分法查找
*/
function searchInWhile( $array, $toSearch ) {
// 第一个元素的索引
$low = 0;
// 数组最后一个元素的索引
$high = count( $array ) - 1;
while ( $low <= $high ) {
// 取得数组的中间键值
$mid = intval( ( $low + $high ) / 2 );
if ( $array[ $mid ] == $toSearch ) {
//如果取出中间的下标值跟你要搜索的值相等的话,直接去除值得下标就行
return $mid;
break;
} elseif ( $array[ $mid ] > $toSearch ) {
$high = $mid - 1;
} else {
$high = $mid + 1;
}
}
}
//
$array = array( 3, 4, 5, 7, 8, 9, 10 );
$toSearch = 9;
echo "要查找的值在数组内的索引 = ".searchRecursive( $array, $toSearch );
echo "\n";
$arr = array( 2, 4, 5, 6, 7, 8, 9, 10 );
$search = 6;
echo "要查找的值在数组内的索引 = ".searchInWhile( $arr, $search );
?>

本文介绍了二分查找算法的多种实现方式,包括Java、C++、Python和PHP四种语言的具体实现,展示了递归和循环两种不同的方法,并提供了查找未命中时的处理方案。
11万+

被折叠的 条评论
为什么被折叠?



