【JZOJ4916】完全背包问题 题解

题目大意

  有 nn 种物品,体积分别为 v1,,vnv_1,\cdots,v_n,每种物品无限个。
  现在有 mm 次询问,每次询问给定一个容量为 ww 的背包,问是否存在一种物品选择方案,使背包恰好装满。同时,要求所选物品中,体积不小于 LL 的物品总数量不超过 CC 件。
  n50,  m105,  w1018n \le 50,\ \ m \le 10^5,\ \ w \le 10^{18}
  vi10000,  L20000,  C30v_i \le 10000,\ \ L \le 20000,\ \ C \le 30

题解

  设 nn 种物品中最小的是 v1v_1
  若 v1Lv_1 \ge L,即全是大件物品,那么总体积不超过 maxviC\max{v_i} \cdot C,用暴力一点的 dp 搞掉。以下讨论 v1<Lv_1 < L 的情况。

  经典套路:设 dpi,jdp_{i,j} 表示:用了 jj 件大件物品和若干小件物品,使得体积 modv1\bmod v_1 等于 ii ,的最小体积。询问答案的时候直接看 dpw mod v1,0Cdp_{w\ \bmod\ v_1, 0\cdots C} 是否小于等于 ww 即可。(因为如果存在合法方案,那么这个合法方案去掉 v1v_1 的物品之后必然满足总体积 w\le w 且体积 modv1=wmodv1\bmod v_1 = w \bmod v_1 且大件物品不超过 CC
  然后观察这个转移,我们选大件物品的话,转移到 j+1j+1 没什么问题,但是如果选小件物品,就会出现后效性,即这个转移路径是个环。
  这里有两种解决方法:第一种是把 dp 转移看成最短路问题,跑个 dijkstra 或者 spfa;第二种是,观察发现转移中出现的环都是简单环,假设是体积 V1V2V3V1V_1 \to V_2 \to V_3 \to \cdots \to V_1,那么这些 VV 中必有一个 dp 值最小的 VxV_x,它不可能从 Vx1V_{x-1} 转移而来,这样就破环为链了,可以顺序 dp 了。