python 二分查找的遞歸與非遞歸實現(xiàn)

二分查找定義

二分查找,又稱折半查找,是對一組有序的數(shù)字進行查找腹忽,其思想如下:

  1. 將待查的數(shù)據(jù)x與數(shù)字的中值mid進行比較,如相等則查找成功砚作,返回x在arr中的索引窘奏;若x>mid,則執(zhí)行2葫录;若x<mid着裹,則執(zhí)行3
  2. 只檢查右邊的數(shù)據(jù),重復1米同,直到arr下標low>=high時結(jié)束
  3. 只檢查左邊的數(shù)據(jù)骇扇,重復1,直到arr下標low>=high時結(jié)束

遞歸實現(xiàn)

import time

# 二分查找(遞歸實現(xiàn))
def binarySearch(arr, low, high, x):
    '''
    該函數(shù)用于實現(xiàn)二分查找
    :param arr: 存儲數(shù)據(jù)的數(shù)組
    :param low: 第一個元素的下標
    :param high: 最后一個元素下標
    :param x: 待查找的數(shù)據(jù)
    :return: mid面粮,數(shù)據(jù)所在的索引
    '''

    if low <= high:
        mid = int((low + high) / 2)
        if x == arr[mid]:
            # 返回索引
            return mid

        # 元素小于中間位置元素少孝,只需要再比較左邊的元素
        if x < arr[mid]:
            return binarySearch(arr, low, mid - 1, x)

        # 元素大于中間位置元素,只需要再比較右邊的元素
        if x > arr[mid]:
            return binarySearch(arr, mid + 1, high, x)

    else:
        return -1


# 測試數(shù)組
arr = ['a', 'b', 'c', 'd']
x = '1'

# 開始時間
start = time.clock()

# 函數(shù)調(diào)用
result = binarySearch(arr, 0, len(arr) - 1, x)

# 結(jié)束時間
end = time.clock()

# 輸出
if result != -1:
    print('元素在數(shù)組中的索引為:{}'.format(result))

else:
    print('元素不在數(shù)組中熬苍!')

# 輸出函數(shù)運行的時間
print(end - start)

非遞歸實現(xiàn)

# python非遞歸實現(xiàn)二分查找

def BinarySearch(arr, low, high, x):
    while True:
        if low <= high:
            mid = int((low + high) / 2)
            if arr[mid] == x:
                return mid
            elif x < arr[mid]:
                high = mid - 1
            else:
                low = mid + 1

        else:
            return -1


# 測試數(shù)組
arr = [1, 2, 3, 4, 5, 6, 7, 8]
x = 10

# 調(diào)用函數(shù)
index = BinarySearch(arr, 0, len(arr) - 1, x)

# 輸出結(jié)果
print('{x}在arr中的索引為{index}'.format(x=x, index=index))

注意本文在遞歸與非遞歸方法中稍走,mid的取值公式mid = int(low + high) / 2,這里相當于是向下去取整了冷溃,即當arr = [1,2,3,4,5,6,7,8]時钱磅,low = 0,high = 7似枕,此時,mid = int((0 + 7) / 2) = int(3.5) = 3年柠,所以第一輪的比較是x4進行比較凿歼,若此時x>4,則下一輪的比較則會變成x6進行比較了冗恨,因為我們是向下取整答憔,所以選的是6

補充

  1. Python中math模塊有專用的向下向上取整函數(shù),以下以代碼示例給出:
import math

f = 5.63
# 向上取整
print(math.ceil(f))
# 向下取整
print(math.floor(f))
# 四舍五入
print(round(f))
# 向下取整返回的類型
print(type(math.floor(f)))

執(zhí)行結(jié)果

image.png

可以看到掀抹,取整函數(shù)返回的結(jié)果的類型是int虐拓,因此,上式mid = int(low + high) / 2也可以換成mid = math.floor((low + high) / 2)

  1. 二分查找的關鍵在于mid = int(low + high) / 2傲武,正式因為這個式子蓉驹,我們才可以每次都從中間取一個數(shù)城榛。根據(jù)實際情況,我們也可以修改該式子态兴,比如:mid = int(low + high) / 3狠持,mid取值方式不同,算法的性能也可能不同
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末瞻润,一起剝皮案震驚了整個濱河市喘垂,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌绍撞,老刑警劉巖正勒,帶你破解...
    沈念sama閱讀 216,651評論 6 501
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異傻铣,居然都是意外死亡昭齐,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,468評論 3 392
  • 文/潘曉璐 我一進店門矾柜,熙熙樓的掌柜王于貴愁眉苦臉地迎上來阱驾,“玉大人,你說我怎么就攤上這事怪蔑±锔玻” “怎么了?”我有些...
    開封第一講書人閱讀 162,931評論 0 353
  • 文/不壞的土叔 我叫張陵缆瓣,是天一觀的道長喧枷。 經(jīng)常有香客問我,道長弓坞,這世上最難降的妖魔是什么隧甚? 我笑而不...
    開封第一講書人閱讀 58,218評論 1 292
  • 正文 為了忘掉前任,我火速辦了婚禮渡冻,結(jié)果婚禮上戚扳,老公的妹妹穿的比我還像新娘。我一直安慰自己族吻,他們只是感情好帽借,可當我...
    茶點故事閱讀 67,234評論 6 388
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著超歌,像睡著了一般砍艾。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上巍举,一...
    開封第一講書人閱讀 51,198評論 1 299
  • 那天脆荷,我揣著相機與錄音,去河邊找鬼。 笑死蜓谋,一個胖子當著我的面吹牛梦皮,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播孤澎,決...
    沈念sama閱讀 40,084評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼届氢,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了覆旭?” 一聲冷哼從身側(cè)響起退子,我...
    開封第一講書人閱讀 38,926評論 0 274
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎型将,沒想到半個月后寂祥,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,341評論 1 311
  • 正文 獨居荒郊野嶺守林人離奇死亡七兜,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,563評論 2 333
  • 正文 我和宋清朗相戀三年丸凭,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片腕铸。...
    茶點故事閱讀 39,731評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡惜犀,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出狠裹,到底是詐尸還是另有隱情虽界,我是刑警寧澤,帶...
    沈念sama閱讀 35,430評論 5 343
  • 正文 年R本政府宣布涛菠,位于F島的核電站莉御,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏俗冻。R本人自食惡果不足惜礁叔,卻給世界環(huán)境...
    茶點故事閱讀 41,036評論 3 326
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望迄薄。 院中可真熱鬧琅关,春花似錦、人聲如沸噪奄。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,676評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽勤篮。三九已至,卻和暖如春色罚,著一層夾襖步出監(jiān)牢的瞬間碰缔,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,829評論 1 269
  • 我被黑心中介騙來泰國打工戳护, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留金抡,地道東北人瀑焦。 一個月前我還...
    沈念sama閱讀 47,743評論 2 368
  • 正文 我出身青樓,卻偏偏與公主長得像梗肝,于是被迫代替她去往敵國和親榛瓮。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 44,629評論 2 354

推薦閱讀更多精彩內(nèi)容