[英]How can I make this algorithm more efficient for a puzzle?
難題是:給定一個數字n
,我需要返回一個數組,其中包含所有數字的平方和等於n^2
的遞增序列。 例如: [3,4]
是一個有效的解決方案,因為3^2 + 4^2 = 25
,但是對於n = 50
, [1, 1, 4, 49]
不會因為1, 1
不是遞增序列. 測試還提到,如果兩個或多個序列是有效的,我們應該選擇最終數字最大的一個。 如果沒有找到解決方案,它應該返回None
。 然后,我編寫了這段代碼,它成功地通過了n
為5
和8
的兩個初步測試,但在更大的測試中超時,這是可以預測的。 那么,我怎樣才能使它更有效率呢? 我正在考慮使用生成器,但無法決定在哪里:
def decompose(n):
add = []
result = []
for i in range (n-1, 0, -1):
if sum(add) < n ** 2:
add.append(i**2)
result.append(i)
elif sum(add) > n ** 2:
add.pop()
result.pop()
elif sum(add) == n ** 2:
return sorted(result)
return None
這並未針對速度進行優化,但確實提供了正確的解決方案。 訣竅是使用遞歸。 這個問題的關鍵變量不僅是 n 本身,而且是列表中元素必須具有的總和。 最初這是 n**2,但每次添加新元素時,剩余總和都會降低,之后可以添加到列表中的最大 integer 也會降低。 因此,向列表中添加一個新數字又是一個老問題,但有不同的約束。 這使得這是一個遞歸問題,也是何時使用yield
和yield from
的一個很好的例子。
def decompose(max_n, sum_allowed, solution):
for x in range(max_n, 0, -1):
left_over_sum = sum_allowed - x**2
if left_over_sum == 0:
yield [x] + solution
elif left_over_sum > 0:
yield from decompose(x-1, left_over_sum, [x] + solution)
yield None
def decompose_top(n):
generator = decompose(n-1, n**2, [])
return next(generator)
print(decompose_top(1000001))
在這台 7 年的機器上,我只需一秒鍾的執行時間就可以輕松地將 go 變為 n=100000。 通過多次調用生成器上的 next(),可以看到給定 n 的所有可能解決方案。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.