uva 1152 4 values whose sum is zero ——yhx

The SUM problem can be formulated as follows: given four lists A;B;C;D of integer values, compute
how many quadruplet (a; b; c; d) 2 AB C D are such that a+b+c+d = 0. In the following, we
assume that all lists have the same size n.
Input
The input begins with a single positive integer on a line by itself indicating the number of the cases
following, each of them as described below. This line is followed by a blank line, and there is also a
blank line between two consecutive inputs.
The rst line of the input le contains the size of the lists n (this value can be as large as 4000).
We then have n lines containing four integer values (with absolute value as large as 228) that belong
respectively to A;B;C and D.
Output
For each test case, your program has to write the number quadruplets whose sum is zero.
The outputs of two consecutive cases will be separated by a blank line.

 1 #include<cstdio>
 2 #include<cstring>
 3 int abs(int x)
 4 {
 5     if (x>=0) return x;
 6     return -x;
 7 }
 8 const int m=1098469;
 9 int a[4010],b[4010],c[4010],d[4010],first[1100000],next[17000000],num[17000000];
10 int main()
11 {
12     int i,j,k,n,p,q,x,y,z,t,ans;
13     scanf("%d",&t);
14     while (t--)
15     {
16         memset(a,0,sizeof(a));
17         memset(b,0,sizeof(b));
18         memset(c,0,sizeof(c));
19         memset(d,0,sizeof(d));
20         memset(first,0,sizeof(first));
21         memset(next,0,sizeof(next));
22         memset(num,0,sizeof(num));
23         ans=0;
24         scanf("%d",&n);
25         for (i=1;i<=n;i++)
26           scanf("%d%d%d%d",&a[i],&b[i],&c[i],&d[i]);
27         for (i=1;i<=n;i++)
28           for (j=1;j<=n;j++)
29           {
30               x=a[i]+b[j];
31               p=abs(x%m);
32               next[(i-1)*n+j]=first[p];
33               first[p]=(i-1)*n+j;
34               num[(i-1)*n+j]=x;
35           }
36         for (i=1;i<=n;i++)
37           for (j=1;j<=n;j++)
38           {
39               x=-c[i]-d[j];
40               p=abs(x%m);
41               for (k=first[p];k;k=next[k])
42                 if (x==num[k]) ans++;
43           }
44         printf("%d\n",ans);
45         if (t) printf("\n");
46     }
47 }

枚举a+b,把所有值存起来,然后枚举-c-d,在a+b中查找。

具体查找方法是哈希,除k取余法即可。

时间: 2024-10-12 19:53:10

uva 1152 4 values whose sum is zero ——yhx的相关文章

(白书训练计划)UVa 1152 4 Values whose Sum is 0(中途相遇法。。)

题目地址:UVa 1152 先枚举A集合与B集合的和,存起来,然后再枚举C集合与D集合的和,看与存起来的值有多少个是互为相反数的.水题.找存起来的值时可以用二分找. 代码如下: #include <iostream> #include <cstdio> #include <string> #include <cstring> #include <stdlib.h> #include <math.h> #include <ctyp

UVA 1152 4 Values whose Sum is 0

题意: 四个集合,要求每个集合中选出一个数字,四个数字相加为0,问四个数字相加为零的次数有几次 分析: 先把A+B的和存到sum数组里,然后再从中找-(c+b)出现的个数.求长度为n的有序数组a中的数k的个数num:num=upper_bound(a,a+n,k)-lower_bound(a,a+n,k); 代码: #include <iostream>#include <cstdio>#include <cstring>#include <algorithm&g

UVA 1152 4 Values Whose Sum is Zero 和为0的4个值

摘要:中途相遇.对比map,快排+二分查找,Hash效率. n是4000的级别,直接O(n^4)肯定超,所以中途相遇法,O(n^2)的时间枚举其中两个的和,O(n^2)的时间枚举其他两个的和的相反数,然后O(logN)的时间查询是否存在. 首先试了下map,果断TLE //TLE #include<cstdio> #include<algorithm> #include<map> using namespace std; const int maxn = 4001; i

1152 - 4 Values whose Sum is 0(好用的hash标记,多重循环简单化)

不得不说这个题就是炫酷啊! 首先说一说思路吧,是这么想的: 1.弄四重循环,爆破,明显会超时. 2.为了处理多重循环,就枚举a+b+c,只需要在d中找到a+b+c的相反数即可,超时 3.枚举a+b,只需要在c+d中找到a+b的相反数即可,TMD超时! 4.循环只能优化到这个程度了,再优化就得用哈希表直接调用了. 这个题的哈希表也是新的知识,由于本题a+b的值可能很大很大,所以以前的哈希表检索不好用了(因为数组开不了那么大),多亏高神的Blog,学了一招,哈哈,下面是搬运的内容: 对于一个无法用数

1152 - 4 Values whose Sum is 0

紫书上叫中途相遇法,还有一个名字感觉更加妥帖一点,叫:折半枚举.          有时候,当问题的规模较大时,无法枚举所有元素的组合,但能够枚举一半的元素组合,此时,将问题拆成两半后分别枚举,再合并他们的结果这一方法往往非常有效. 两重循环加二分,总复杂度为n^2logn 这里值得一提的是对集合CD的存储方式,我是用了一个有序数组,也可以用其他方式. #include<bits/stdc++.h> using namespace std; const int max_n =4005; int

UVa 1152 4Values whose Sum is 0

题意  从4个n元集中各挑出一个数  使它们的和为零有多少种方法 直接n^4枚举肯定会超时的  可以把两个集合的元素和放在数组里  然后排序 枚举另外两个集合中两元素和  看数组中是否有其相反数就行了  复杂度为n^2*logn #include <bits/stdc++.h> #define l(i) lower_bound(s,s+m,i) #define u(i) upper_bound(s,s+m,i) using namespace std; const int N = 4005;

K - 4 Values whose Sum is 0(中途相遇法)

K - 4 Values whose Sum is 0 Crawling in process... Crawling failed Time Limit:9000MS     Memory Limit:0KB     64bit IO Format:%lld & %llu Submit Status Practice UVA 1152 Appoint description: System Crawler (2015-03-12) Description The SUM problem can

POJ 2785 4 Values whose Sum is 0(折半枚举)

4 Values whose Sum is 0 Time Limit: 15000MS   Memory Limit: 228000K Total Submissions: 17088   Accepted: 4998 Case Time Limit: 5000MS Description The SUM problem can be formulated as follows: given four lists A, B, C, D of integer values, compute how

uva 11235 - Frequent values(RMQ)

题目链接:uva 11235 - Frequent values 题目大意:给定一个非降序的整数数组,要求计算对于一些询问(i,j),回答ai,ai+1,-,aj中出现最多的数出现的次数. 解题思路:因为序列为非降序的,所以相同的数字肯定是靠在一起的,所以用o(n)的方法处理处每段相同数字的区间.然后对于每次询问: num[i]=num[j]:j?i+1 numi≠numj:max(RMQ(righti+1,reftj?1),max(righti?i+1,j?leftj+1)) #include