Tiling Terrace
\[ Time Limit: 1000 ms\quad Memory Limit: 262144 kB \]
题意
给出一个字符串 \(s\),每次可以选择三种类型来获得价值
\(Type1:“.”\) 获得 \(w_1\) 元
\(Type2:“..”\) 获得 \(w_2\) 元
\(Type3:“.\#.”\) 获得 \(w_3\) 元
此外,还有两个限制条件
\(Limti1:Type1\) 至多只能选 \(K\) 个
\(Limit2:\) 每个字符只能被选择一次
问最多可以获得的价值。
思路
首先可以发现,对于两个相邻的 \(\#\),如果我们确定了这两个的状态,也就是不用或者当成 \(Type3\) 来用,那么我们就可以知道这两个 \(\#\) 之间可用 \(.\) 的数量。如果这个数量是奇数,那么意味着其中有一个 \(.\) 拿来用作 \(Type1\) 是必然不会亏的,也就是这个 \(.\) 是白嫖的。
令 \(dp[i][j][k][0/1]\) 表示到第 \(i\) 个 \(\#\) 号为止,白嫖了 \(j\) 个 \(Type1\),选了 \(k\) 个 \(Type3\),并且第 \(i\) 个 \(\#\) 是否当成 \(Type3\) 来用。
为了方便计算,我们可以在整个字符串的开头加入一个 \(\#\),整个字符串的结尾加入一个 \(\#\),那么整个的状态必然要从 \(dp[0][0][0][0]\) 开始递推,必然以 \(dp[\#_{number}][j][k][0]\) 结尾。
这样推出来以后,我们就知道了白嫖 \(a\) 个 \(Type1\),选 \(c\) 个 \(Type3\) 的情况下,最多可以获得多少个 \(b\)。最后对 \(a、b、c\) 贪心求答案,尝试在 \(Type1\) 不超过 \(K\) 的情况下把 \(Type2\) 换成 \(Type1\)。
我们可以发现,由于 \(\#\) 的个数最多就 \(50\) 个,那么白嫖的 \(Type1\) 必然不会超过 \(51\),所以整个 \(dp\) 的复杂度是 \(O\left(50^3\times4\right)\) 的
/***************************************************************
> File Name : J.cpp
> Author : Jiaaaaaaaqi
> Created Time : Tue 05 Nov 2019 10:00:31 PM CST
***************************************************************/
#include