最近开始在poj上a题,感觉poj上的题质量确实比自己学校oj的题好的多,难度也有比较大的提升,建议初学者在刷够一定量水题后还是在poj上混混,有更快的长进;
这道题是一道动态规划的题目,看到题目,原先我是想用dfs暴力过的,后来看网上用的都是记忆化搜索后,就研究了下别人的代码,发现确实是一道典型的dp题,哎,做题不够多,思路就是不够广啊。
这题主要的思想就是先定义一个结构体,安放该点对应的坐标和高度,然后用优先队列将其从大到小排列,这样的好处,就是在搜索的时候只需单向搜索即可,然后用dp数组来储存每点对应的最长上升序列的值。
这是AC代码:
#include<cstdio>
#include<iostream>
#include<cstring>
#include<queue>
using namespace std;
int map[105][105],dp[105][105];
int dir[4][2]={1,0,-1,0,0,1,0,-1};
struct node
{
int x,y,h;
friend bool operator <(node a,node b)
{
return a.h<b.h;
}
};
int main(void)
{
int r,c;
while(cin>>r>>c)
{
priority_queue<node> qq;
for(int i=0;i<r;i++)
for(int j=0;j<c;j++)
{
cin>>map[i][j];
node q;
q.h=map[i][j];
q.x=i;
q.y=j;
qq.push(q);
}
memset(dp,0,sizeof(dp));
while(!qq.empty())
{
node p;
p=qq.top();
qq.pop();
for(int i=0;i<4;i++)
{
int x=p.x+dir[i][0];
int y=p.y+dir[i][1];
if(x<0||y<0||x>=r||y>=c||(map[x][y]>=map[p.x][p.y]))
continue;
dp[x][y]=max(dp[x][y],dp[p.x][p.y]+1);
}
}
int res=0;
for(int i=0;i<r;i++)
for(int j=0;j<c;j++)
{
res=max(res,dp[i][j]);
}
cout<<res+1<<endl;
}
}