Problem Id Title
1141 Problem A 六神无主
1142 Problem B 追踪器
1143 Problem C Game
1144 Problem D 计算罚时
1145 Problem E 超级整除2
1146 Problem F 3xian的抽象画

    题目比较水,除了最后一个题,都不发代码了  

    PRO A:  直接模拟除法 

    PRO B:  直接比较,输出答案

    PRO C:SRM DIV1 470 1000P的原题,求一个最大生成树的总权值

    PRO D:  模拟,不过要按照时间拍下序,用两个MAP来记录

    PRO E: 鸽巢原理

    PRO F:   

    此题是很好的一道题, 首先要维护一个栈,来维护这个序列,每当遇到'(' 进栈,遇到')'出栈,那么这个括号序列就是个欧拉序列了~,根据这个欧拉序列建一个树,而且还要记录树的高度,每个节点的高度 = max( 儿子节点的高度 ) + 1。 这个时候若父节点被覆盖,则子节点不用被覆盖,若子节点没覆盖,则孙子节点要覆盖,就这样,最大需要覆盖的面积为第一个父节点的(右值 - 左值) * 高度,不需要覆盖的就为子节点的面积,这样算下去,用一个BFS每层处理很方便,代码有点猥琐,凑合着看,由于int错了一次,于是一次性全部把int 换成 LL。

代码
1 #include <iostream>
2 #include <stack>
3
4  using namespace std;
5
6  const int maxn = 400009;
7
8 typedef __int64 LL;
9
10 struct node {
11 LL v;
12 node* next;
13 } *adj[maxn], edge[maxn];
14
15 struct tree {
16 LL l, r, cnt, high, f;
17 } tt[maxn] ;
18
19 LL e_num, tot, len;
20 char in[maxn];
21
22 void add_edge(LL u, LL v)
23 {
24 node* ptr = &edge[ e_num ++ ];
25 ptr -> v = v;
26 ptr -> next = adj[u];
27 adj[u] = ptr;
28 }
29
30 void init()
31 {
32 e_num = tot = 0;
33 for(LL i=0; i < maxn; i++) {
34 tt[i].high = 0;
35 adj[i] = NULL;
36 }
37 }
38
39 stack<LL> s;
40 void built()
41 {
42 LL father = 0;
43 for(LL i=0; i < len; i++)
44 {
45 if(in[i] == '(') {
46 tot ++;
47 tt[ tot ].l = i;
48 tt[ tot ].f = father;
49 add_edge(father , tot);
50 father = tot;
51 s.push( tot );
52 } else {
53 LL now = s.top(); s.pop();
54 tt[ now ].r = i;
55 for(node* ptr = adj[ now ]; ptr; ptr = ptr -> next)
56 tt[ now ].high = max( tt[ now ].high , tt[ ptr -> v ].high );
57 tt[now].high ++;
58 father = tt[ now ].f;
59 }
60 }
61 }
62
63 struct xiaowu { LL cnt, u; } que[maxn], tmp, nxt;
64
65 LL bfs(LL now)
66 {
67 LL head = 0 , tail = 0;
68 LL area = (tt[now].r - tt[now].l) * tt[now].high;
69
70 tmp.cnt = 1;
71 tmp.u = now;
72
73 que[tail ++] = tmp;
74
75
76 while(head != tail)
77 {
78 tmp = que[head ++]; head %= maxn;
79
80 for(node* ptr = adj[tmp.u]; ptr; ptr = ptr -> next)
81 {
82 LL v = ptr -> v;
83 if(tmp.cnt == 1)
84 area -= tt[ v ].high * ( tt[ v ].r - tt[ v ].l ) ;
85 else
86 area += tt[ v ].high * ( tt[ v ].r - tt[ v ].l ) ;

89 nxt.u = v;
90 nxt.cnt = tmp.cnt * -1;
91 que[tail ++] = nxt;
92 tail %= maxn;
93 }
94 }
95
96 return area;
97 }
98
99 LL solve()
100 {
101 LL area = 0;
102 for(node* ptr = adj[0]; ptr ; ptr = ptr -> next)
103 {
104 LL son = ptr -> v;
105 area += bfs( son );
106 }
107 return area;
108 }
109
110 int main()
111 {
112 //freopen("in.in", "r", stdin);
113 int cas;
114 cin >> cas;
115 while(cas --)
116 {
117 init();
118 cin >> in;
119 len = strlen( in );
120 built();
121 printf("%I64d\n", solve());
122 }
123 return 0;
124 }
125

 

 

   

posted on 2010-05-30 23:17  xIao.wU 思维磁场  阅读(250)  评论(0编辑  收藏  举报