GOJ 1146

[栈]http://222.200.98.145:8000/JudgeOnline/showproblem?problem_id=1146

  这题解法不多,我只想到递归式解法.这道题想出解法不难,但如果对栈没有很好地理解实现起来是很棘手的.递归的解法最容易想了,但这里字符串长度可达350000, 递归很容易TLE, 曾写过一个递归的,TLE了. 只能用递归的思想->栈来写,也就是说用栈模拟递归.

  解法思路: 从字符串左往右遍历, 遇到'(' , 放进栈里, 栈size加1.遇到')'时,开始处理.前面必有一个'('与之对应,则这对'()'里的总面积就可以求出来了,处理过程要不停保存当前'()'的长度和高度. 外面一层'()'面积等于里面那层的(长度+1)*(高度+1).这是主要的递推式.处理好这一环,这题就迎刃而解了.在提交的时候出现一点奇怪的事,当数据以"lld"格式输出时oj判错,当数据以"I64d"输出时,AC!!..oj的编译器标明是g++,却对__64int支持得那么好而不是long long..不解.

代码
1 #include <iostream>
2 #include <cstdio>
3 #include <cstring>
4  using namespace std;
5
6 const int MAXN=350010;
7 long long len[MAXN], high[MAXN];
8
9 long long Max(long long a, long long b)
10 {
11 return a<b?b:a;
12 }
13 int main()
14 {
15 int T;
16 char str[MAXN];
17 long long stack, ans;
18 scanf("%d", &T);
19 while( T-- )
20 {
21 ans=stack=0;
22 scanf("%s", str);
23 for( int i=0; str[i]!='\0'; ++i )
24 {
25 if( str[i]=='(' )
26 {
27 stack++;
28 }
29 else
30 {
31 ans+=(high[stack+1]+1)*(len[stack+1]+1)*(stack%2==0?-1:1);
32 high[stack]=Max(high[stack+1]+1, high[stack] );
33 len[stack]+=len[stack+1]+2;
34 high[stack+1]=len[stack+1]=0;
35 if( stack==1 )
36 high[1]=len[1]=0;
37 stack--;
38 }
39 }
40 printf("%lld\n", ans);
41 }
42 return 0;
43 }
44

posted on 2010-11-21 16:05  Kenfly  阅读(447)  评论(0编辑  收藏  举报