zoukankan      html  css  js  c++  java
  • 背包相关问题总结

    至多与恰好

    如果问恰好装(v),则初始化(dp[]=-INF,dp[0]=0)。二维(dp)则初始化(dp[][]=-INF,dp[0][0]=0)。(这样就能是那些能够恰好装满背包的物品的值为正数,而那些不能恰好装满背包的物品的值就为负数。)

    如果问至多装(v),则初始化(dp[]=0)

    一定要注意,要求恰好时,分组背包枚举某一组的元素之前,要再设(dp[j]=-INF)。((INF)的值要够小!)

    二维(dp)时(要求恰好),最开始的(max)也可能要设(-INF)(除了第一次时)

    01背包和完全背包枚举顺序

    01背包是倒序,完全背包是顺序。

    (若倒序枚举,(j)只会一直减小,所以我们总是用第(i-1)个阶段向第(i)个阶段转移,是01背包。如果是正序,那么(j)有可能被(j-v_i)更新。(j)增大到(j+v_i)时,又可能被(j)更新。这时两个都处于第(i)个阶段的状态之间发生了转移,相当于第(i)个物品被使用了两次,是完全背包。)

    分组背包枚举顺序

    先枚举是哪个组(i),再倒序枚举体积(j),最后再枚举每组组内元素(k)

    (注意枚举顺序。(i)是阶段,(i)(j)共同构成状态,而(k)是决策。)

    多重背包枚举顺序

    思想:转化为共有(sumlimits_{i=1}^{n}k_i)个物品的01背包问题((k_i)是每种物品的个数)。

    先枚举是哪种物品(i),再枚举(i)的个数(j),最后再倒序枚举体积(k),做01背包dp[k]=max(dp[k],dp[k-w[i]]+c[i])

    注意res=max{dp[0~v]}

    二进制拆分法(优化多重背包)

    原来的多重背包时间复杂度是(O(Vsumlimits_{i=1}^nk_i))的,效率较低。

    我们可以把数量为(k_i)的第(i)种物品拆成(p+2)个物品((p)是满足(2^0+2^1+2^2+...+2^ple{k_i})的最大整数)。

    它们的体积分别为(2^0*w_i,2^1*w_i,...,2^p*w_i,r_i*w_i)(r_i=k_i-sumlimits_{i=0}^p2^i))。

    那么这(p+2)个物品可以且只能凑成(0sim{k_i}*w_i)之间所有能被(k_i)整除的数,这等价于原问题中体积为(w_i)的物品可以使用(0sim{k_i})次。这时的复杂度是(O(Vsumlimits_{i=1}^nlog(k_i)))

  • 相关阅读:
    SVD singular value decomposition
    Eigen参考资料
    设置C++ cout输出精度
    eigenMatrix
    电池容量单位 Wh和 Ah的关系
    windows10 如何关闭快速关机功能电源选项
    TIA Portal 和 scout 之间的驱动器地址分配
    SIMATIC 1500 PLC 同步轴,状态字StatusWord信号描述
    Simotion 凸轮同步,偏移凸轮起点
    ROS Create a Catkin Workspace
  • 原文地址:https://www.cnblogs.com/andysj/p/13881650.html
Copyright © 2011-2022 走看看