马蹄印
题目大意:
有一个只含括号的图,要你走一条路(从左上角出发),使你走的路上的括号加在一起是先k个左括号再k个右括号组成的,要求k最大
原题:
题目描述:
虽然当奶牛贝里斯找到平衡序列后很高兴了,但是他现在对序列提出了一个更高的要求,就是要求每个序列中必须是先一定数量的左括号然后是与左括号相同数量的右括号。例如:(((()))),就是一个完美的平衡序列。
当贝里斯某天在农场上走的时候,他在地上发现了马蹄印,这个农场是一个N*N的方格,每个小方格中都有一个马蹄印。贝里斯希望从方格的最左上角的地方开始出发,然后每次可以向上或者向下或者向左或者向右移动一步,使得他走过的每个小方格中的马蹄印能够组成一个完美的平衡序列。当然了,贝里斯不能重复经过任何小方格。
问题描述:
请帮助贝里斯在这个N*N的方格中找出长度最长的完美序列的长度。
输入
第一行一个正整数N,表示农场的大小。
接下来N行,每行N个字符,表示N*N的方格上马蹄印的分布情况。
输出
只有一行一个整数,表示最长的完美序列的长度,如果不存在这样的完美序列(例如起始位置就是右括号),则输出0。
输入样例
4
(())
()((
(()(
))))
输出样例
8
说明
数据范围:2<=N<=5。
说明:样例中,奶牛的行走序列是这样的:
1())
2)((
345(
876)
解题思路:
因为数据太小,所以直接DFS就可以了
代码:
#include<cstdio>
#include<string>
#include<cstring>
#include<iostream>
using namespace std;
int n,ans,p[10][10];
char a[10][10];
string str;
const int dx[4]={0,-1,0,1};
const int dy[4]={1,0,-1,0};
bool check(int xx,int yy)
{if (xx>0&&xx<=n&&yy>0&&yy<=n&&!p[xx][yy]) return true;//判断是否没出界,没到过return false;
}
void dfs (int x,int y,int l,int r)
{if (l==r){ans=max(ans,l+r);//已经走完了return;}for (int i=0;i<4;++i)if (check(x+dx[i],y+dy[i])){p[x+dx[i]][y+dy[i]]=1;if (a[x+dx[i]][y+dy[i]]=='('&&!r)//要没有走过右括号dfs(x+dx[i],y+dy[i],l+1,r);if (a[x+dx[i]][y+dy[i]]==')')dfs(x+dx[i],y+dy[i],l,r+1);p[x+dx[i]][y+dy[i]]=0;//清零}
}
int main()
{scanf("%d",&n);getchar();for (int i=1;i<=n;++i){cin>>str;for (int j=1;j<=n;++j)a[i][j]=str[j-1];//读入}p[1][1]=1;//初值if (a[1][1]==')') putchar(48);else dfs(1,1,1,0),printf("%d",ans);//输出
}