hdu_1069_Monkey and Banana hdu_1078_FatMouse and Cheese poj_1836_Alignment

hdu_1069_Monkey and Banana

http://acm.hdu.edu.cn/showproblem.php?pid=1069

天花板上挂着一些香蕉,Monkey想要吃(Monkey不够高),于是Monkey想利用n个石块中的一些(长方体形状)堆起来,每层的石块的长和宽都要比前面一层的小(不可相等),这样Monkey才能爬上去,石块不限量。

考虑到石块可以转,所以每种石块有3种有效状态(如 10*20*30的石块,三种有效状态的长宽高分别是 30*20*10、30*10*20、20*10*30);由此也可以知道一种石块不可能使用超过3次。所以我们可以当做有3*n种不可转的石块。

首先进行排序,按长宽从大到小排序。

dp[i] 表示以第i种石块作为顶的最高可以有多高。我们要在前i-1种情况下找出能放下第i种石块的最高的情况。

dp[i]=max(dp[0...i-1]+s) //s为第i种石块的高。(==加了一个石块表示地面,即长宽等于INF,高为0,这样所有的石块都可以放置在这个”地面石块上面“)

#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
using namespace std;

#define INF 100000000

struct Node {
	int x,y,z;
	void set (int X,int Y,int Z){
		x = X;
		y = Y;
		z = Z;
	}
};

bool cmp (Node a,Node b){
	if (a.x==b.x) return a.y>b.y;
	else return a.x>b.x;
}

int main(){
	int n;int c=1;
	while (cin>>n,n){
		int a[3];
		Node s[200];
		int dp[200];
		memset (dp,0,sizeof(dp));
		for (int i=0;i<n;i++){
			for (int j=0;j<3;j++)
				cin>>a[j];
			sort(a,a+3);
			s[i*3+0].set(a[2],a[1],a[0]);
			s[i*3+1].set(a[2],a[0],a[1]);
			s[i*3+2].set(a[1],a[0],a[2]);
		}
		s[n*3].set(INF,INF,0);
		sort (s,s+n*3+1,cmp);

		dp[0]=0;
		int t;
		for (int i=1;i<=3*n;i++){
			t=0;
			for (int j=i-1;j>=0;j--){
				if (s[j].x>s[i].x&&s[j].y>s[i].y){
					if (dp[t]<dp[j]){
						t=j;
					}
				}
			}
			dp[i]=dp[t]+s[i].z;
		}
		for (int i=1;i<=3*n;i++){
			dp[0]=max(dp[0],dp[i]);
		}
		cout<<"Case "<<c++<<": maximum height = "<<dp[0]<<endl;
	}
}

hdu_1078_FatMouse and Cheese

http://acm.hdu.edu.cn/showproblem.php?pid=1078

FatMouse 在一些存放了奶酪的”网格“里(位置<0,0>),因为外面有只猫,说以FatMouse每次最多只能走k步,当然,FatMouse可以往上下左右四个方向走。FatMouse每到一个网格就要吃掉网格里的奶酪,为了维持能量,FatMouse每次吃的奶酪都要比上一次吃的大。求FatMouse最多能吃多少奶酪。

看着像求一个最大和上升子序列,可是是二维的。wiking 说的把坐标存起来换成一维的。

结构体存奶酪大小和坐标(x,y),按奶酪大小排序,比(0,0)位置小的奶酪就不用理他了。

dp[i][j]表示以第[i][j]奶酪为最后吃的的最大值。dp[i][j]=max(dp[x][y]+a[i][j]);(dp[x][y]<a[i][j]) [x][y] 是可以走到ij的位置,有4个方向最多4*k个位置。

==这样我一直wa,因为即使a[i][j]>a[0][0],还是有可能没有(x,y)可以到达他的,不删除的话就会多一个起点。

#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
using namespace std;

struct Node {
	int v,x,y;
};

bool cmp (Node a,Node b){
	return a.v<b.v;
}

int main (){
	int n,k;
	while (cin>>n>>k){
		if (n==-1&&k==-1){
			break;
		}
		int a[106][106],v=0;
		int dp[106][106];
		int use[106][106];
		memset(dp,0,sizeof(dp));
		memset(use,0,sizeof(use));
		Node s[10010];
		for (int i=0;i<n;i++){
			for (int j=0;j<n;j++){
				scanf ("%d",&a[i][j]);
				s[v].x=i;s[v].y=j;
				s[v].v=a[i][j];
				v++;
			}
		}
		int ans=a[0][0],i;
		// cout<<v<<endl;
		sort (s,s+v,cmp);
		for (i=0;i<v;i++){
			if (s[i].x==0&&s[i].y==0) {
				dp[0][0]=a[0][0];i++;
				break;
			}
			use[s[i].x][s[i].y]=1;
		}
		// cout<<s[i].x<<" "<<s[i].y<<endl;
		for (i;i<v;i++){
			int X,Y,maxn=-1;
			X=s[i].x;Y=s[i].y;
			for (int j=1;j<=k;j++){
				if (X+j<n&&a[X+j][Y]<s[i].v&&!use[X+j][Y]){
					maxn=max(maxn,dp[X+j][Y]);
				}
				if (Y-j>=0&&a[X][Y-j]<s[i].v&&!use[X][Y-j]){
					maxn=max(maxn,dp[X][Y-j]);
				}
				if (X-j>=0&&a[X-j][Y]<s[i].v&&!use[X-j][Y]){
					maxn=max(maxn,dp[X-j][Y]);
				}
				if (Y+j<n&&a[X][Y+j]<s[i].v&&!use[X][Y+j]){
					maxn=max(maxn,dp[X][Y+j]);
				}
			}//cout<<maxn<<endl;
			if (maxn==-1) use[X][Y]=1;
			dp[X][Y]=maxn+s[i].v;
			ans=max(ans,dp[X][Y]);
			// cout<<ans<<endl;
			//cout<<s[i].x<<" "<<s[i].y<<" "<<s[i].v<<" ";
		}
		cout<<ans<<endl;
	}
	return 0;
}

poj_1836_Alignment

http://poj.org/problem?id=1836

队长检查士兵,n个士兵们排队高矮不齐,队长希望提出几个士兵,使得队伍里的每个士兵左边或右边的士兵都比他矮。

从左往右求LIS dp0[i]表示已i为结尾的最长子序列长度。

从右往左求LIS dp1[j]表示已j为结尾的最长子序列长度。

然后枚举i和j求出最小的n-dp0[i]-dp1[j];注意dp0[n-1]和dp1[0]两种特殊情况。

<pre name="code" class="cpp">#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>

using namespace std;

#ifndef INF
#define INF 1000000000
#endif

int n;

void solve (double a[],int dp[]){
	dp[0]=0;
	for (int i=0;i<n;i++){
		dp[i]=1;
		for (int j=0;j<i;j++){
			if (a[i]>a[j]){
				dp[i]=max(dp[i],dp[j]+1);
			}
		}
	}
}

void swapd (int dp[0]){
	for (int i=0;i<n/2;i++){
		swap(dp[i],dp[n-1-i]);
	}
}

int main(){
	double a[1010],b[1010];
	int dp0[1010],dp1[1010];
	memset(dp0,0,sizeof(dp0));
	cin>>n;
	for (int i=0;i<n;i++){
		cin>>a[i];
		b[n-1-i]=a[i];
	}
	solve(a,dp0);
	solve(b,dp1);
	swapd(dp1);
	/*for (int i=0;i<n;i++){
		printf ("%d ",dp0[i]);
	}printf ("\n");
	for (int i=0;i<n;i++){
		printf ("%d ",dp1[i]);
	}printf ("\n");
	cout<<endl;*/
	int ans=min(n-dp0[n-1],n-dp1[0]);
	for (int i=0;i<n-1;i++){
		for (int j=i+1;j<n;j++){
			ans=min(ans,n-dp0[i]-dp1[j]);
		}
	}
	cout<<ans<<endl;
	return 0;
}

dp总是水我这样好吗==

时间: 2024-10-12 18:08:29

hdu_1069_Monkey and Banana hdu_1078_FatMouse and Cheese poj_1836_Alignment的相关文章

[2016-03-30][HDU][1069][Monkey and Banana]

时间:2016-03-27 15:19:40 星期日 题目编号:[2016-03-30][HDU][1069][Monkey and Banana] 题目大意:给定n种积木无限个,问这些积木最大能叠多高,上面的积木长宽必须严格小于下面的积木 分析: dp[i]表示第i个积木在顶部时候的最大高度,那么dp[i] = max(dp[i],dp[j] + h[i]);?ji能放在j上面?ji能放在j上面 初始条件就是长宽最大的高度是它自己, #include <algorithm> #include

[2016-03-28][HDU][1078][FatMouse and Cheese]

时间:2016-03-28 17:40:34 星期一 题目编号:[2016-03-28][HDU][1078][FatMouse and Cheese] #include <algorithm> #include <cstring> #include <cstdio> using namespace std; const int maxn = 100 + 10; int a[maxn][maxn]; int dp[maxn][maxn]; int n ,k; int d

记忆化搜索,FatMouse and Cheese

1.从gird[0][0]出发,每次的方向搜索一下,每次步数搜索一下 for(i=0; i<4; i++) { for(j=1; j<=k; j++) { int tx=x+d[i][0]*j; int ty=y+d[i][1]*j; if(tx>=0&&tx<n&&ty>=0&&ty<n&&grid[x][y]<grid[tx][ty]) { int temp=memSearch(tx,ty); i

HDU1078 FatMouse and Cheese 【内存搜索】

FatMouse and Cheese Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 4966    Accepted Submission(s): 2035 Problem Description FatMouse has stored some cheese in a city. The city can be considere

UVA1001 Say Cheese

如果没有洞,那么任意两点的最短距离就是直线距离,洞里是瞬间的,所以看成一个点就行了(其实点也可以当作半径为0的洞来处理),洞到洞的最短距离都是圆心距离减去半径.剩下的就是完全图求单源最短路径,用不加堆优化的dijkstra就行了O(n^2). #include<bits/stdc++.h> using namespace std; typedef long long ll; const int maxn = 102; int x[maxn],y[maxn],z[maxn],r[maxn]; d

hdu 1078 FatMouse and Cheese

Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submission(s): 5701    Accepted Submission(s): 2320 Problem Description FatMouse has stored some cheese in a city. The city can be considered as a square grid of

HDOJ 1069 Monkey and Banana 【DP】

Monkey and Banana Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 8610 Accepted Submission(s): 4452 Problem Description A group of researchers are designing an experiment to test the IQ of a monke

BZOJ2021: [Usaco2010 Jan]Cheese Towers

2021: [Usaco2010 Jan]Cheese Towers Time Limit: 4 Sec  Memory Limit: 64 MBSubmit: 184  Solved: 107[Submit][Status] Description Farmer John wants to save some blocks of his cows' delicious Wisconsin cheese varieties in his cellar for the coming winter.

HDU1078:FatMouse and Cheese(记忆化)

Problem Description FatMouse has stored some cheese in a city. The city can be considered as a square grid of dimension n: each grid location is labelled (p,q) where 0 <= p < n and 0 <= q < n. At each grid location Fatmouse has hid between 0 a