Python演算法題----在列表中找到和為s的兩個數字
阿新 • • 發佈:2019-02-02
列表data的值為[1, 3, 4, 5, 8, 9, 11],找出這個列表中和為13的兩個數字的所有組合。這個好找,上過幼兒園大班的,估計都能找出來。4+9=13, 5+8=13。如何用python寫一個函式來實現呢。
解法一:
超級大迴圈
最容易想到的就是遍歷啊。巢狀迴圈,外層迴圈遍歷全部列表,內層迴圈遍歷當前元素位置之後的所有元素。內層迴圈中將兩個數字相加,等於13就break。妥妥找到。
def equalSum01(data=None, twosum=13):
result = []
for i, vi in enumerate(data):
if i + 1 > len(data) - 1:
break
for j, vj in enumerate(data[i+1:]):
if vi + vj == twosum:
print(vi, vj)
result.append((vi, vj))
break
return result
解法二:
首尾相加法
因為data是升序排列的一個列表,我們可以用兩個指標l, r指向列表的兩端,那麼data[l]+data[r]的和有3種情況:
1、等於S,那就將這兩個數字新增的結果列表中,l指標右移,r指標左移
2、小於S, 將l指標右移
3、大於S, r指標左移
def equalSum02(data=None, twosum=13):
result = []
l = 0
r = len(data) - 1
while l < r:
if data[l] + data[r] == twosum:
result.append((data[l], data[r]))
l += 1
r -= 1
elif data[l] + data[r] < twosum:
l += 1
else:
r -= 1
return result
解法三:
精準搜尋法
遍歷data, 期待值 = S - data[i], 如果這個期待值在data[i]右面的剩餘列表中,則找到,遍歷萬一遍,也就找到了所有的。
def equalSum03(data=None, twosum=13):
result = []
for i, v in enumerate(data):
if (twosum - v) in data[i+1:]:
result.append((v, twosum - v))
return result
從時間複雜度上來說,解法一是時間複雜度最大的一個。解法三因為每次迴圈都要搜尋剩餘的列表,應該大於解法二。
單元測試
import unittest
class TestInverseMethods(unittest.TestCase):
def test_equalSum01(self):
data = [1, 3, 4, 5, 8, 9, 11]
result = [(4, 9), (5, 8)]
self.assertEqual(equalSum01(data), result)
def test_equalSum02(self):
data = [1, 3, 4, 5, 8, 9, 11]
result = [(4, 9), (5, 8)]
self.assertEqual(equalSum02(data), result)
def test_equalSum03(self):
data = [1, 3, 4, 5, 8, 9, 11]
result = [(4, 9), (5, 8)]
self.assertEqual(equalSum03(data), result)
if __name__ == ‘__main__‘:
unittest.main()
...
----------------------------------------------------------------------
Ran 3 tests in 0.000s
OK
(4, 9)
(5, 8)