• 区间DP


    内容参考书籍《算法竞赛入门到进阶》

    区间DP就是先在小区间进行DP,然后合并小区间,得到大区间,直到解决最后的大区间问题。相较于普通的DP问题,它不仅需要状态转移方程还需要枚举所有可能的区间。

    通常情况下,区间DP至少需要两层for循环,例如:

    	for (int i = 1; i < n; ++i)
    	{
    		for (int j = i; j <= n; ++j)
    		{
    			...
    		}
    	}
    

      下面引入两个经典问题:

    1.石子合并:有n堆石子排成一排,每堆石子有一定的数量,将这n堆石子合成一堆,每次只能合并相邻的两堆,合并花费为两堆石子总数,求最小花费。

    输入:

    3
    2 4 5
    

    输出:

    17
    

    计算过程为:一:2+4=6,二:6+5=11,三:6+11=17,故答案为17。

    设dp[i][j]为从第i堆石子到第j堆石子的最小花费,那么答案为dp[1][n]。另外,设sum[i][j]为从第i到j的区间和。

    那么合并两堆,例如dp[1][2],是指合并1-2,就有dp[1][2] = dp[1][1] + dp[2][2] + sum[1][2],也即是dp[i][i+1] = dp[i][i] + dp[i+1][i+1] + sum[i][i+1]

    合并三堆,例如dp[1][3],则有两种情况,先合并1-2再3,或者先2-3再1,即dp[1][3] = min(dp[1][1] +dp[2][3], dp[1][2] + dp[3][3])+sum[1][3]。

    也即是dp[i][i+2] = min(dp[i][i]+dp[i+1][i+2] , dp[i][i+1] + dp[i+2][i+2])+sum[i][i+2]。

    推广:dp[i][j] = min(dp[i][k]+dp[k+1][j])+sum[i][j-i+1]。

    代码如下:

    (后续代码明天写)

  • 相关阅读:
    python 发包爬取中国移动充值页面---可判断手机号是否异常
    python利用selenium和safari浏览器驱动实现新浪微博自动点赞 Demo
    Django学习报错记录
    nginx和tomcat的区别
    Mac主机映射到域名
    mac下eclipse安装svn插件-subclipse
    移动端——等分,居中
    移动端——重置样式
    M端页面-绝对定位布局
    jquery-练习-折叠效果
  • 原文地址:https://www.cnblogs.com/125418a/p/12952824.html
Copyright © 2020-2023  润新知