标签:
题解:
设定dp[1][n]位最后答案
每次去删除2个或者3个连续,或不连续的数
暴力区间dp
我是用dfs写的比较好理解
#include <iostream> #include <cstdio> #include <cmath> #include <cstring> #include <algorithm> #include<map> using namespace std; const int N = 315, M = 30005, mod = 1e9 + 7, inf = 0x3f3f3f3f; typedef long long ll; int dp[N][N]; ll a[N],d; map<ll,int > mp; int dfs(int l,int r) { if(dp[l][r]!=-1) return dp[l][r]; int& ret = dp[l][r]; ret = 0; if(l>=r) return ret; if(l+1==r) { if(mp[a[r]-a[l]]) return (ret = 2); else return (ret = 0); } int tmp = 0; if(mp[a[r]-a[l]]) tmp+=2; if(dfs(l+1,r-1)==((r-1)-(l+1)+1)) ret = tmp+((r-1)-(l+1)+1); tmp = 0; if(a[l+1]-a[l]==a[r]-a[l+1]&&mp[a[r]-a[l+1]]) tmp+=3; if(dfs(l+2,r-1) == ((r-1)-(l+2)+1))ret = max(ret,tmp+((r-1)-(l+2)+1)); tmp = 0; if(a[r-1]-a[l]==a[r]-a[r-1]&&mp[a[r]-a[r-1]]) tmp+=3; if(dfs(l+1,r-2) == ((r-2)-(l+1)+1)) ret = max(ret,tmp+((r-2)-(l+1)+1)); for(int i=l+1;i<r;i++) { ret = max(ret,dfs(l,i)+dfs(i+1,r)); } return ret; } int main() { int T,m,n; scanf("%d",&T); while(T--) { mp.clear(); memset(dp,-1,sizeof(dp)); scanf("%d%d",&n,&m); for(int i=1;i<=n;i++) scanf("%I64d",&a[i]); for(int i=1;i<=m;i++) scanf("%I64d",&d),mp[d] = 1; printf("%d\n",dfs(1,n)); } return 0; }
2016"百度之星" - 初赛(Astar Round2A) 1004 D Game 区间DP
标签:
原文地址:http://www.cnblogs.com/zxhl/p/5517993.html