首页 > 学院 > 开发设计 > 正文

UVA - 10118 Free Candies 记忆化搜索经典

2019-11-08 02:14:40
字体:
来源:转载
供稿:网友

            思路:d[a][b][c][d]表示从已经第一个篮子取了a颗糖,第二个取了b颗糖,第三个取了c颗糖,第四个取了d颗糖最多还能够获得多少糖果。首先明白一个问题:如果能分别取a,b,c,d个,不论如何取,最后篮子中剩余的糖果颜色和个数都是一样的。那么一旦搜索到一个已经被搜索过得状态,直接返回即可,没必要继续搜索。

  AC代码:

#include<cstdio>#include<algorithm>#include<cstring>#include<utility>#include<string>#include<iostream>#include<map>#include<set>#include<vector>#include<queue>#include<stack>using namespace std;#define eps 1e-10#define inf 0x3f3f3f3f#define PI pair<int, int> const int maxn = 40 + 2;int cand[4][maxn], n;int d[maxn][maxn][maxn][maxn];int top[4], bit[30];void init() {	bit[0] = 1;	for(int i = 1; i < 22; ++i) bit[i] = bit[i-1] * 2;}int dfs(int color, int cnt) {	if(d[top[0]][top[1]][top[2]][top[3]] != -1) 		return d[top[0]][top[1]][top[2]][top[3]];	if(cnt == 5) return d[top[0]][top[1]][top[2]][top[3]] = 0;	int ans = 0;	for(int i = 0; i < 4; ++i) {		if(top[i] >= n) continue;		int col = ++top[i];		col = bit[cand[i][col]];		if(col & color) { //篮子中已经右该颜色 			 int a = 1 + dfs(color - col, cnt - 1);			 ans = max(ans, a);		}		else {			int a = dfs(color + col, cnt + 1);			ans = max(ans, a);		}		top[i]--;	}	return d[top[0]][top[1]][top[2]][top[3]] = ans;}int main() {	init();	while(scanf("%d", &n) == 1 && n) {		memset(d, -1, sizeof(d));		memset(top, 0, sizeof(top));		for(int i = 1; i <= n; ++i) 			for(int j = 0; j < 4; ++j) 				scanf("%d", &cand[j][i]); 		PRintf("%d/n", dfs(0, 0));	}	return 0;}如有不当之处欢迎指出!


发表评论 共有条评论
用户名: 密码:
验证码: 匿名发表