原题为一棵二叉搜索树,第 i 个点需要询问 ai 次,每次询问走的长度为路径经过点的个数。求最小的询问经过点个数。
5
8 3 1 2 4
35
样例解释是 4 为 1 的右儿子,2 和 5 为 4 的儿子,3 是 2 的儿子,每个点经过 ai 次查询后最小经过点的个数是 35。n⩽5×103。
这题显然是用区间 DP 四边形不等式解的,但是关键在于中间枚举转移点的部分:
for(register int k=w[i][j-1];k<=w[i+1][j];k++){
if(dp[i][k-1]+dp[k+1][j]<=dp[i][j]){
dp[i][j]=dp[i][k-1]+dp[k+1][j];
w[i][j]=k;
}
}
这一份代码是 AC 的,然而下面这一份,仅仅是改为小于号
for(register int k=w[i][j-1];k<=w[i+1][j];k++){
if(dp[i][k-1]+dp[k+1][j]<dp[i][j]){
dp[i][j]=dp[i][k-1]+dp[k+1][j];
w[i][j]=k;
}
}
他的意思大概就是使决策点统一往左边偏,上面的那一份则是决策点统一往右边偏,但是对此题有极大影响,不知道是什么原因,有人可以解答一下吗?/yiw
是否是由于此题的特性使得往左偏的计算次数更多,还是四边形不等式往右边偏计算次数一定更少?
而且我们还发现不同的区间 DP 写法时间的差别貌似有点大/yiw