Skip to content

Commit f0827cf

Browse files
committed
update binary search
1 parent e9080c3 commit f0827cf

File tree

3 files changed

+88
-15
lines changed

3 files changed

+88
-15
lines changed
4.95 KB
Loading

binary_search/binary_search.py

+63-15
Original file line numberDiff line numberDiff line change
@@ -1,28 +1,76 @@
11
#!/usr/bin/env python
22
# -*- coding: utf-8 -*-
33
# Created by imoyao at 2019/5/13 18:33
4+
import os
5+
import sys
46

7+
try:
8+
from ..util import utils
9+
except ValueError:
10+
currpath = os.path.join(os.getcwd(), os.path.dirname(__file__))
11+
relative_fp = os.path.dirname(currpath)
12+
print(relative_fp)
13+
sys.path.append(relative_fp)
14+
from util import utils
515

6-
def binary_search(sorted_lists, wanted_item):
16+
17+
@utils.show_time
18+
def binary_search_while(sorted_lists, wanted_item):
19+
"""
20+
二分查找( while 实现)
21+
:param sorted_lists: 有序数组
22+
:param wanted_item: 需要查找的元素
23+
:return: 索引值 / None
24+
"""
725
low_index = 0
8-
high_index = len(sorted_lists) - 1
9-
count = 0
26+
high_index = len(sorted_lists) - 1 # 查找范围为整个有序列表的索引
27+
_count = 0
1028
while low_index <= high_index:
11-
count += 1
12-
mid_index = (low_index + high_index) // 2
13-
# print(mid_index)
29+
_count += 1
30+
mid_index = (low_index + high_index) // 2 # py3中的整数除
1431
mid_item = sorted_lists[mid_index]
1532
if mid_item == wanted_item:
16-
print('It takes {0} times to find {1} in index {2}'.format(count, wanted_item, mid_index))
17-
return mid_item
33+
print('It takes {0} times to find {1} in index {2}'.format(_count, wanted_item, mid_index))
34+
return mid_index
35+
elif mid_item < wanted_item: # 如果猜的值小于目的值,则在大端继续查找
36+
low_index = mid_index + 1
1837
else:
19-
if mid_item < wanted_item:
20-
low_index = mid_index + 1
21-
else:
22-
high_index = mid_index - 1
23-
return None
38+
high_index = mid_index - 1 # 否则,在小端查找
39+
return None # 没有找到,返回None
40+
41+
42+
count = 0
43+
44+
45+
@utils.show_time
46+
def binary_search_recurse(sorted_lists, wanted_item, low_index=0, high_index=None):
47+
"""
48+
二分查找(递归实现)
49+
:param sorted_lists: 有序序列
50+
:param wanted_item: 查找的元素
51+
:param low_index: 开始位索引
52+
:param high_index: 结束位索引
53+
:return: 索引值 / None
54+
"""
55+
global count
56+
57+
if high_index is None:
58+
high_index = len(sorted_lists) - 1
59+
60+
mid_index = (low_index + high_index) // 2
61+
mid_item = sorted_lists[mid_index]
62+
count += 1
63+
if low_index > high_index: # 注意此处,表示遍历序列,也没找到
64+
return None
65+
if mid_item < wanted_item: # 猜值小于目的值,则在大端继续查找
66+
return binary_search_recurse(sorted_lists, wanted_item, mid_index + 1, high_index)
67+
elif mid_item > wanted_item: # 小端查找
68+
return binary_search_recurse(sorted_lists, wanted_item, low_index, mid_index - 1)
69+
70+
print('It takes {0} times to find {1} in index {2}'.format(count, wanted_item, mid_index))
71+
return mid_index
2472

2573

2674
if __name__ == '__main__':
27-
a = binary_search(list(range(100)), 50)
28-
print('ret:', a)
75+
print(binary_search_while(list(range(100)), 0))
76+
print(binary_search_recurse(list(range(100)), 0, 0, len(list(range(100))) - 1))

binary_search/describe.md

+25
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
# 简单查找和二分搜索
2+
3+
## 引言
4+
5+
> 富翁子不识字,人劝以延师训子。先学一字是一画,次二字是二画,次三字三画。其子便欣然投笔告父曰:“儿已都晓字义,何用师为?”父喜之乃谢去。一日父欲招万姓者饮,命子晨起治状,至午不见写成。父往询之,子恚曰:“姓亦多矣,如何偏姓万,自早至今才得五百画哩!”
6+
>
7+
> <right> ——《笑林广记》· 训子(古艳部)</right>
8+
9+
以上便是`线性查找`,线性查找也叫`简单查找`,或者更加通俗的叫法“傻找”。就是从头找到尾,直到符合条件了才返回。
10+
11+
## 概念
12+
13+
在计算机科学中,`二分搜索`(binary search),也称折半搜索(half-interval search)、对数搜索(logarithmic search),是一种在**有序数组**中查找某一特定元素的搜索算法。搜索过程**从数组的中间元素开始**,如果中间元素正好是要查找的元素,则搜索过程结束;如果某一特定元素大于或者小于中间元素,则在数组大于或小于中间元素的那一半中查找,而且跟开始一样从中间元素开始比较。如果在某一步骤数组为空,则代表找不到。这种搜索算法每一次比较都使搜索范围缩小一半。
14+
15+
## 图示
16+
17+
![二分搜索算法](./Binary_search_into_array.png)
18+
19+
## 复杂度
20+
21+
O(log(n))
22+
23+
## 扩展
24+
25+
[`bisect`-列表的二等分算法](https://docs.python.org/3.6/library/bisect.html)

0 commit comments

Comments
 (0)