记忆化搜索练习题

题目描述

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(从24开始,在1结束)。当然25-24-23―┅―3―2―1更长。事实上,这是最长的一条。

输入输出格式

输入格式:

输入的第一行为表示区域的二维数组的行数R和列数C(1≤R,C≤100)。下面是R行,每行有C个数,代表高度(两个数字之间用1个空格间隔)。

扫描二维码关注公众号,回复: 2554174 查看本文章

输出格式:

输出区域中最长滑坡的长度。

输入输出样例

输入样例#1: 复制

5 5
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

输出样例#1: 复制

25

大致思路:

题目描述

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(从24开始,在1结束)。当然25-24-23―┅―3―2―1更长。事实上,这是最长的一条。

输入输出格式

输入格式:

输入的第一行为表示区域的二维数组的行数R和列数C(1≤R,C≤100)。下面是R行,每行有C个数,代表高度(两个数字之间用1个空格间隔)。

输出格式:

输出区域中最长滑坡的长度。

1.我们开两个数组,一个用来存放数字和步数,另一个存放每个结点可以走到的最哒大高度

2.我们循环每个点,从每个点出发进行DP搜索

3.搜索的过程中为了避免重复搜索,我们当一个点已经搜索过的时候,可以直接利用这个点已经存放好的最大高度进行计算

4.只需要求出所有最大高度数组中的最大值,就是答案

代码:

#include<iostream>
using namespace std;
const int maxn = 110;
struct node {
	int num;
	int step;
}arr[maxn][maxn];
int ans[maxn][maxn];
int m, n;
int dir[4][2] = 
{
	{-1,0},
    {0,1},
    {1,0},
    {0,-1}
};
int MAXN = -1;
int MAXN2 = -1;
void bfs(int x,int y)
{
	for (int i = 0; i < 4; i++)
	{
		int nx = x + dir[i][0];
		int ny = y + dir[i][1];
		if (nx > 0 && ny > 0 && nx <= m && ny <= n)
		{
			if (arr[nx][ny].num < arr[x][y].num)
			{
				if (ans[nx][ny] > 0&&ans[nx][ny]+arr[x][y].step>MAXN)
				{
					MAXN = ans[nx][ny] + arr[x][y].step;
				}
				else
				{
					arr[nx][ny].step = arr[x][y].step + 1;
					if (arr[nx][ny].step > MAXN)
					{
						MAXN = arr[nx][ny].step;
					}
					bfs(nx, ny);
					
				}
				arr[nx][ny].step = 1;
			}
		}
	}
}
void find_ans()
{
	for (int i = 1; i <= m; i++)
	{
		for (int j = 1; j <= n; j++)
		{
			MAXN = 1;
			bfs(i, j);
			ans[i][j] = MAXN;
			arr[i][j].step = 1;
			if (ans[i][j] > MAXN2)
			{
				MAXN2 = ans[i][j];
			}
		}
	}
}
int main()
{
	cin >> m >> n;
	for (int i = 1; i <= m; i++)
	{
		for (int j = 1; j <= n; j++)
		{
			cin >> arr[i][j].num;
			arr[i][j].step = 1;
		}
	}
	find_ans();
	cout << MAXN2;
	system("pause");
}
/*
6 6
1 2 3 4 5 6
12 11 10 9 8 7
18 17 16 15 14 13
24 23 22 21 20 19
30 29 28 27 26 25
36 35 34 33 32 31
*/

猜你喜欢

转载自blog.csdn.net/scwMason/article/details/81358700