POJ 1088 滑雪
将点排序,再按从小到大的顺序DP
滑雪
Time Limit: 1000MS | Memory Limit: 65536K | |
Total Submissions: 65761 | Accepted: 24114 |
Description
Michael喜欢滑雪百这并不奇怪, 因为滑雪的确很刺激。可是为了获得速度,滑的区域必须向下倾斜,而且当你滑到坡底,你不得不再次走上坡或者等待升降机来载你。Michael想知道载一个区域中最长底滑坡。区域由一个二维数组给出。数组的每个数字代表点的高度。下面是一个例子
1 2 3 4 5
16 17 18 19 6
15 24 25 20 7
14 23 22 21 8
13 12 11 10 9
一个人可以从某个点滑向上下左右相邻四个点之一,当且仅当高度减小。在上面的例子中,一条可滑行的滑坡为24-17-16-1。当然25-24-23-...-3-2-1更长。事实上,这是最长的一条。
1 2 3 4 5
16 17 18 19 6
15 24 25 20 7
14 23 22 21 8
13 12 11 10 9
一个人可以从某个点滑向上下左右相邻四个点之一,当且仅当高度减小。在上面的例子中,一条可滑行的滑坡为24-17-16-1。当然25-24-23-...-3-2-1更长。事实上,这是最长的一条。
Input
输入的第一行表示区域的行数R和列数C(1 <= R,C <= 100)。下面是R行,每行有C个整数,代表高度h,0<=h<=10000。
Output
输出最长区域的长度。
Sample Input
5 5
1 2 3 4 516 17 18 19 615 24 25 20 714 23 22 21 813 12 11 10 9
Sample Output
25
Source
POJ 下C++提交通过,G++RE
1 #include <iostream> 2 #include <algorithm> 3 #include <cstring> 4 5 using namespace std; 6 7 int a[210][210]; 8 9 struct dot 10 { 11 int x,y; 12 int h; 13 }; 14 15 bool cmp(dot a,dot b) 16 { 17 if(a.h>b.h) return false; 18 else return true; 19 } 20 21 dot ddd[20010]; 22 23 int dp[210][210]; 24 25 const int dx[4]={-1,1,0,0}; 26 const int dy[4]={0,0,-1,1}; 27 28 int main() 29 { 30 int C,R; 31 cin>>R>>C; 32 33 memset(a,0,sizeof(a)); 34 int cur=0; 35 for(int i=1;i<=R;i++) 36 for(int j=1;j<=C;j++) 37 { 38 cin>>a[i][j]; 39 ddd[cur].x=i; 40 ddd[cur].y=j; 41 ddd[cur].h=a[i][j]; 42 cur++; 43 } 44 45 sort(ddd,ddd+cur,cmp); 46 47 memset(dp,0,sizeof(dp)); 48 49 for(int i=0;i<cur;i++) 50 { 51 for(int j=0;j<4;j++) 52 { 53 int X=ddd[i].x+dx[j]; 54 int Y=ddd[i].y+dy[j]; 55 if(X>=1&&X<=R&&Y>=1&&Y<=C) 56 if((a[X][Y]>ddd[i].h)&&(dp[X][Y]<dp[ddd[i].x][ddd[i].y]+1)) 57 dp[X][Y]=dp[ddd[i].x][ddd[i].y]+1; 58 } 59 } 60 61 int maxn=-99999; 62 63 for(int i=1;i<=R;i++) 64 { 65 for(int j=1;j<=C;j++) 66 { 67 // cout<<dp[i][j]<<" "; 68 maxn=max(maxn,dp[i][j]); 69 } 70 // cout<<endl; 71 } 72 73 cout<<maxn+1<<endl; 74 75 return 0; 76 }