2012 Multi-University Training Contest 4
2012-08-03 13:40
246 查看
1004 hdu 4334 http://acm.hdu.edu.cn/showproblem.php?pid=4334
题意:
给定五个集合,从五个集合中分别取出5个数,如果存在满足a1 + a2 + a3 + a4 +a5 == 0 输出yes,否则no; 集合的大小小于200 ai的取值为 [-10^15, 1 0^15]
思路:
开始的时候O(n^2)求出前两个集合的所有可能的和,然后O(n^3)+二分log(10^4)做,结果竟然tle。。坑爹啊。。。。最后用了hash过的。好像poj有个类似的题目,也是hash做的。
hash开散列两种实现方式,
挂链:
View Code
题意:
给定五个集合,从五个集合中分别取出5个数,如果存在满足a1 + a2 + a3 + a4 +a5 == 0 输出yes,否则no; 集合的大小小于200 ai的取值为 [-10^15, 1 0^15]
思路:
开始的时候O(n^2)求出前两个集合的所有可能的和,然后O(n^3)+二分log(10^4)做,结果竟然tle。。坑爹啊。。。。最后用了hash过的。好像poj有个类似的题目,也是hash做的。
hash开散列两种实现方式,
挂链:
View Code
#include <iostream> #include <cstdio> #include <cmath> #include <cstring> #define maxn 1000007 using namespace std; int val[4*maxn]; char s1[maxn],s2[maxn]; void pushup(int rt) { val[rt] = val[rt<<1] + val[rt<<1|1]; } void build(int l,int r,int rt) { if (l == r) { if (s1[l] == s2[l]) val[rt] = 0;//相同为0,不同为1 else val[rt] = 1; return ; } int m = (l + r)>>1; build(l,m,rt<<1); build(m + 1,r,rt<<1|1); pushup(rt); } void update(int pos,char *sc,int l,int r,int rt,int mk) { if (l == r) { if (mk == 1) s1[l] = sc[0]; if (mk == 2) s2[l] = sc[0]; if (s1[l] == s2[l]) val[rt] = 0; else val[rt] = 1; return ; } int m = (l + r)>>1; if (pos <= m) update(pos,sc,l,m,rt<<1,mk); else update(pos,sc,m + 1,r,rt<<1|1,mk); pushup(rt); } int getsum(int L,int R,int l,int r,int rt) { if (l >= L && r <= R) { return val[rt]; } int res = 0; int m = (l + r)>>1; if (L <= m) res += getsum(L,R,l,m,rt<<1); if (R > m) res += getsum(L,R,m + 1,r,rt<<1|1); return res; } int query(int pos,int l,int r,int rt) { if (l == r) return l; int res = 0; int m = (l + r)>>1; if (pos <= val[rt<<1]) res = query(pos,l,m,rt<<1); else { pos -= val[rt<<1]; res = query(pos,m + 1,r,rt<<1|1); } return res; } int main() { int t; int x,y; char z[3]; int cas = 1; scanf("%d",&t); while (t--) { scanf("%s%s",s1,s2); int len1 = strlen(s1); int len2 = strlen(s2); int len = max(len1,len2); build(0,len,1); int q,op; scanf("%d",&q); printf("Case %d:\n",cas++); while (q--) { scanf("%d",&op); if (op == 2) { scanf("%d",&x); if (s1[x] != s2[x]) printf("0\n"); else { int ret = getsum(0,x,0,len,1);//首先找出[0,x]不同的点的个数 ret++;//++后就是要查找的第几个不同的点了 int pos = query(ret,0,len,1);//返回第ret个不同点的位置 printf("%d\n",pos - x); } } else { scanf("%d%d%s",&x,&y,z); update(y,z,0,len,1,x); } } } return 0; }
相关文章推荐
- 2012 Multi-University Training Contest 1
- 2012 Multi-University Training Contest 2
- 2012 Multi-University Training Contest 2
- 2012 Multi-University Training Contest 5:Mark the Rope
- 2012 Multi-University Training Contest 6-1001 hdu4350 Card
- hdu 4353 Finding Mine (计算几何 2012 Multi-University Training Contest 6 )
- 2012 Multi-University Training Contest 5 Problem G The Beautiful Road(HDU4346)
- 2012 Multi-University Training Contest 6
- 2012 Multi-University Training Contest 1[hdu4300~4309]
- 2012 Multi-University Training Contest 2
- 2012 Multi-University Training Contest 3
- 2012 Multi-University Training Contest 4
- hdu 4362 Dragon Ball(dp + 优化) (2012 Multi-University Training Contest 7 )
- 2012 Multi-University Training Contest 6
- 2012 Multi-University Training Contest 4[hdu4331~4339]
- hdu 4340 Capturing a country(树形 dp) (2012 Multi-University Training Contest 5 )
- 2012 Multi-University Training Contest 4
- hdu 4370 0 or 1 (最短路 // 01 规划 2012 Multi-University Training Contest 8 )
- HDU 4358 Boring Counting ★★(2012 Multi-University Training Contest 6)
- hdu 4393 Throw nails (2012 Multi-University Training Contest 10 )