假设您想用sum<max_sum和{}和{}之间的元素数来查找输入的所有子集。在

这里有两种方法可以做到这一点,我包含了整个脚本以使它更易于测试和使用,但基本上您只需要*LimitedSums()函数就可以得到答案。在

暴力方法是iterate through all subsets,并检查每个子集的和和和元素数。这实际上就是SlowLimitedSums()所做的——尽管它利用itertools.combinations()来迭代子集,并且不考虑包含超过max_terms元素的子集。在

可能更有效的方法是只考虑总和小于max_sum的子集。如果您正在递归地构建子集,那么只要当前子集的和超过max_sum,假设所有输入数字都是非负的,或者元素的数量超过max_terms,就可以简单地停止递归。这是在^{中实现的。在

请注意,在最坏的情况下,您的结果将包含所有2^len(v)子集,在这种情况下,*LimitedSums()的两个版本之间应该没有明显的运行时间差。在import itertools

import random

def SlowLimitedSums(v, max_sum, min_terms=None, max_terms=None):

min_terms = 0 if min_terms is None else min_terms

max_terms = len(v) if max_terms is None else max_terms

return sorted(set(

sum(c) for nc in range(min_terms, max_terms + 1)

for c in itertools.combinations(v, nc)

if sum(c) <= max_sum))

def FasterLimitedSums(v, max_sum, min_terms=None, max_terms=None):

l = sorted(v)

n = len(v)

min_terms = 0 if min_terms is None else min_terms

max_terms = n if max_terms is None else max_terms

result = set([])

def RecursiveSums(s, n_terms, start_pos):

if start_pos >= n or s > max_sum or n_terms > max_terms:

return

if n_terms >= min_terms:

result.add(s)

for p in range(start_pos, n):

RecursiveSums(s + v[p], n_terms + 1, p + 1)

RecursiveSums(0, 0, -1)

return sorted(result)

def main():

mass_list = [4, 1, 8]

mass = 10

print(sorted(mass_list + SlowLimitedSums(mass_list, mass, min_terms=2)))

print(sorted(mass_list + FasterLimitedSums(mass_list, mass, min_terms=2)))

if __name__ == "__main__":

main()

Logo

GitCode 天启AI是一款由 GitCode 团队打造的智能助手,基于先进的LLM(大语言模型)与多智能体 Agent 技术构建,致力于为用户提供高效、智能、多模态的创作与开发支持。它不仅支持自然语言对话,还具备处理文件、生成 PPT、撰写分析报告、开发 Web 应用等多项能力,真正做到“一句话,让 Al帮你完成复杂任务”。

更多推荐