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

回退背包

回退背包问题(线段树分治):

\(Content\)

给定\(n\)个物品,编号为\(i\)的物品有质量\(w_i\)和价值\(v_i\)以及一个体积\(V\)。初始时背包没有可选物体。

\(m\)次操作,对于每次操作,给出一个整数\(op\)\(x\)

\(op=1\),向背包的可选范围内添加\(x\)号物品;
\(op=2\),从背包的可选范围内删除\(x\)号物品。

每次操作后求01背包的方案数或最大值。

\(Solution:\)

对于方案数:

求方案数的\(dp\)代码如下:

for(int i=1;i<=n;i++)for(int j=V;j>=w[i];j--)f[j]+=f[j-w[i]];

考虑以下一个问题,若每次将一个物体放进可选范围后,下一次操作便将它取出,求方案数呢?
只需要把这件物品的贡献再减去即可,注意要正序枚举
易得以下代码:

for(int j=w[i];j<=V;j++)f[j]-=f[j-w[i]];

而在背包问题中,物体放入背包的顺序对于答案是没有影响的,所以回退背包关于方案数的解法就等价于上面的解法。

板子题
code

对于最大值:

可以发现假发加法是可逆的,但是取\(max\)是不可逆的,所以关于方案数的解法对于最大值问题自然不适用。

对于最大值问题,可以采用线段树分治来做。

首先离线下来所有询问,记录每个物品的放入时间和取出时间。在时间轴上建立一棵线段树,对于线段树的每个节点都开一个\(dp\)数组,然后将每个物品类放入与其有交的区间中。
然后遍历线段树,每一个节点的\(dp\)数组都可以由它的父亲转移而来(父节点的\(dp\)数组加上新增的物品)。
最后每个叶节点的答案就是每个时间点的答案。

但是这样处理空间复杂度太大了。
而我们其实只需要对每一层开一个\(dp\)数组,每次递归重新赋值就足以记录了。

线段树分治板子
code

回退背包维护最大值板子
code

\(Summary:\)

对于回退背包问题,通解是线段树分治,对于求方案数的题目,可以使用一些小技巧来解决。

http://www.rkmt.cn/news/51547.html

相关文章:

  • module jdk.compiler does not “以” com.sun.tools.javac.processing” to unnamed module
  • nginx 响应html内容
  • logicFlow ,画布节点自定义
  • NOIP2025模拟9
  • iOS移动端H5键盘弹出时页面布局异常和滚动解决方案 - 详解
  • 深入解析:Hadoop 集群自动化运维实战
  • PyCharm gitee: Git Pull Failed
  • 【MySQL】实操: 慢SQL优化
  • NCA和fsQCA
  • PyCharm gitee: ignore
  • python方便的桌面应用.customtkinter
  • 全球云服务震荡:Amazon Web Services (AWS) 出现大规模故障 多项线上服务受冲击 - 实践
  • 20232406 2025-2026-1 《网络与系统攻防技术》实验五实验报告
  • 20232315 2025-2026-1 《网络与系统攻防技术》实验五实验报告
  • 2025.11.16模拟赛
  • spark启动方式
  • 20232411 2024-2025-1 《网络与系统攻防技术》实验五实验报告
  • 20232325 2025-2026-1 《网络与系统攻防技术》实验五实验报告
  • 鸿蒙应用开发实战:如何从0到1打造创新应用
  • 2025年11月防冻液厂家推荐榜:五家对比与性能评价一览
  • 2025年11月载冷剂厂家推荐榜:技术资质与口碑综合评测
  • 【第7章 I/O编程与异常】Python文件操作与上下文管理器的深度解析(避坑指南)
  • springboot生成前后端接口文档 - f
  • AI元人文:价值权衡的双模引擎与五维元问——构建人机共生的存在语法
  • Spring Cloud - Spring Cloud 注册中心与服务提供者(Spring Cloud Eureka 概述、微服务高效入门、微服务应用实例)
  • DateUtil
  • (链表)判断是否回文
  • (链表)判断两个单链表是否存在交点
  • (链表)任意删除一个结点
  • 在抖音直播推广开源作品的可行性?