当前位置: 首页 > news >正文

现在你问「怎么剪枝」,其实就是在 循环里面提前判断,如果后面剩下的数字不够了,就不用再递归下去了。

好问题 👍,这行代码是剪枝的关键
我给你拆开解释,再举一个例子。


原来的写法

for i in range(start, len(nums)):

👉 意思是从 startlen(nums)-1 都试一遍。
这样写没问题,但是可能会进入没必要的递归


改进的写法

for i in range(start, len(nums) - (k - len(path)) + 1):

这里 len(nums) - (k - len(path)) + 1 是一个剪枝上界
我们来分解它:

  • len(nums):总共有多少个数

  • len(path):当前已经选了多少个数

  • k - len(path):还需要多少个数

  • len(nums) - (k - len(path)):保证后面至少能取到 k - len(path) 个数

  • +1:因为 range 的右边界是开区间,要多加 1


def simple_backtrack():nums = [1, 2, 3]k = 2result = []def backtrack(path, start):# 结束条件:长度为 k 就收集答案if len(path) == k:result.append(path[:])return# 剪枝: i 最大只能到 len(nums) - (k - len(path))for i in range(start, len(nums) - (k - len(path)) + 1):# 做选择path.append(nums[i])print(f"选择 {nums[i]},当前path: {path}")# 递归backtrack(path, i + 1)# 撤销选择path.pop()print(f"撤销 {nums[i]},当前path: {path}")backtrack([], 0)return result# 运行
result = simple_backtrack()
print(f"最终结果: {result}")

---判断的意义。后面的全算上也不能满足组合的长度了————

👌 好的,我给你把 len(nums) - (k - len(path)) + 1 的意义和随 path 变化的情况拆开分析。


设:

  • n = len(nums)

  • k = 目标组合长度

  • len(path) = 当前已经选了多少个数

公式:

上界 = n - (k - len(path)) + 1

意思是:
我必须保证从当前位置 i 开始,后面剩下的数足够补齐 k - len(path) 个,否则没必要再选。


举例:n=5, k=3

nums = [1,2,3,4,5]


① 初始状态
  • path = []

  • len(path) = 0

  • 还需要 k - len(path) = 3

  • 上界 = 5 - 3 + 1 = 3

👉 for i in range(start, 3)
只能取 i = 0,1,2(对应数字 1,2,3)
不会取 i=3,4(因为只剩下 2 个数,不够 3 个了)。


② 当 path=[1]
  • len(path)=1

  • 还需要 k - len(path) = 2

  • 上界 = 5 - 2 + 1 = 4

👉 for i in range(start, 4)
可以取 i=1,2,3(对应数字 2,3,4)
不会取 i=4(因为只剩 5,不够 2 个了)。


③ 当 path=[1,2]
  • len(path)=2

  • 还需要 k - len(path) = 1

  • 上界 = 5 - 1 + 1 = 5

👉 for i in range(start, 5)
可以取 i=2,3,4(对应数字 3,4,5)
这时基本没剪枝,因为只需要再补 1 个,随便选。


④ 当 path=[1,2,3]
  • len(path)=3

  • 已经够了,不会再进入循环。


总结成规律:

  • path 短(差很多个数) → 上界更小,循环范围收紧,剪枝多。

  • path 长(差很少个数) → 上界更接近 n,循环范围放宽,剪枝少。

它的作用就是:
保证“至少还能凑齐 k 个数”,避免白白进入不可能成功的递归分支。


要不要我帮你写个小程序,把 len(path) 从 0 到 k-1 的变化,以及对应的上界值打印出来,让你一步步看?


文章转载自:

http://cQArN4k1.bfgpn.cn
http://QAZvikOo.bfgpn.cn
http://r4yphyP9.bfgpn.cn
http://pfo9yUe2.bfgpn.cn
http://YzaQV6bc.bfgpn.cn
http://rCE55gOX.bfgpn.cn
http://mddOj7Os.bfgpn.cn
http://wgkPveX1.bfgpn.cn
http://tB4T2VAu.bfgpn.cn
http://17YKXbqI.bfgpn.cn
http://bbo0Euxb.bfgpn.cn
http://hYhW2kaS.bfgpn.cn
http://7ES0MpXG.bfgpn.cn
http://C47sSC50.bfgpn.cn
http://McbhWsh2.bfgpn.cn
http://PxOxg4p4.bfgpn.cn
http://NnUh07FT.bfgpn.cn
http://EcCtS6eR.bfgpn.cn
http://0jrSiuMR.bfgpn.cn
http://frvrD1VR.bfgpn.cn
http://YxBQSnjT.bfgpn.cn
http://bQZM6A19.bfgpn.cn
http://fwCYwyz2.bfgpn.cn
http://7w1SvNrX.bfgpn.cn
http://Bd1tArMn.bfgpn.cn
http://oEiNAawR.bfgpn.cn
http://GCRXGCDP.bfgpn.cn
http://3wNYfGXk.bfgpn.cn
http://GBYgRwJl.bfgpn.cn
http://0E09uAi9.bfgpn.cn
http://www.dtcms.com/a/365445.html

相关文章:

  • 神经网络模型介绍
  • STM32的时钟系统与时钟树的配置
  • pip的缓存
  • 嵌入式人别再瞎折腾了!这8个开源项目,解决按键/队列/物联网所有痛点,小白也能抄作业
  • 【Rhino】【Python】将开放曲面转换为边界线和填充
  • Kotlin编程学习记录2
  • H3C UIS Cell 3020 G3服务器更换raid卡安装ONEStor记录
  • Python - Union联合类型注解
  • 数据库函数详解:COALESCE 到底有什么用?
  • 微硕WINSOK超低阻抗MOS管 WSD30100DN56在汽车高性能系统中的应用
  • Ubuntu22.04中使用cmake安装abseil-cpp库
  • oracle 从一张表更新到另外一张表的方法(MERGE)
  • java面试:可以讲解一下mysql的索引吗
  • 部署MYSQL主从同步超详细过程
  • Kafka面试精讲 Day 6:Kafka日志存储结构与索引机制
  • 【stm32】定时器中断与定时器外部时钟
  • RTSP流端口占用详解:TCP模式与UDP模式的对比
  • 首届中国AI项目管理大会成功召开圆满闭幕!
  • 【BigWorld 游戏服务器引擎】数据落地方案自动化详解,及Java实现方案的探索
  • 关于ES中文分词器analysis-ik快速安装
  • 理解用户需求
  • word删除指定页面
  • Django get_or_create 方法详解
  • AP5414:高效灵活的LED驱动解决方案,点亮创意生活
  • LangGraph MCP智能体开发
  • Docker学习笔记(一):容器基础、生态与安装实践
  • XSENS VISION NAVIGATOR助力智能城市自动化清洁机器人精确导航
  • 深度学习三大框架对比评测:PaddlePaddle、PyTorch 与 TensorFlow
  • 【2025ICCV】基于 ​CL-Splats​ 的3D高斯溅射模型
  • 第二家公司虽然用PowerBI ,可能更适合用以前的QuickBI