[BZOJ2797][Poi2012]Squarks
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了[BZOJ2797][Poi2012]Squarks相关的知识,希望对你有一定的参考价值。
2797: [Poi2012]Squarks
Time Limit: 10 Sec Memory Limit: 64 MBSubmit: 211 Solved: 89
[Submit][Status][Discuss]
Description
设有n个互不相同的正整数{X1,X2,...Xn},任取两个Xi,Xj(i≠j),能算出Xi+Xj。
现在所有取法共n*(n-1)/2个和,要你求出X1,X2,...Xn。
Input
第一行一个正整数n (3<=n<=300)。
第二行n*(n-1)/2个正整数(每个正整数不超过10^8),表示任取两个Xi,Xj(i≠j)算出的n*(n-1)/2个和。
Output
第一行一个正整数k,表示方案数。测试数据保证至少存在一种方案。
下面k行每行给出递增的n个正整数。方案按照{Xi}的最小值从大到小输出。
Sample Input
Sample Input 1
4
3 5 4 7 6 5
Sample Input 2
4
11 17 12 20 21 15
4
3 5 4 7 6 5
Sample Input 2
4
11 17 12 20 21 15
Sample Output
Sample Output 2
2
4 7 8 13
3 8 9 12
Sample Output 1
1
1 2 3 4
2
4 7 8 13
3 8 9 12
Sample Output 1
1
1 2 3 4
HINT
Source
先把数列排一下序,a1一定是x1+x2,a2一定是x1+x3。如果知道x2+x3的话,就可以求出x1~x3了。
这样的话可以枚举x2+x3,然后求出x1~x3之后删掉这里面的和,最小的一定是x1+x4了,这样又可以求出来x4。
因为n比较小,这样就可以过了。
1 #include<set> 2 #include<cstdio> 3 #include<algorithm> 4 #define N 305 5 using namespace std; 6 inline int read() 7 { 8 int x=0,f=1;char ch=getchar(); 9 while(ch<‘0‘||ch>‘9‘){if(ch==‘-‘)f=-1;ch=getchar();} 10 while(ch>=‘0‘&&ch<=‘9‘){x=x*10+ch-‘0‘;ch=getchar();} 11 return x*f; 12 } 13 int n,tot,a[N*N],ans[N][N],x[N]; 14 multiset<int>s; 15 void solve(int a3) 16 { 17 s.clear(); 18 for(int i=1;i<=n*(n-1)/2;i++) 19 s.insert(a[i]); 20 if(a[1]+a[2]+a3&1)return; 21 x[1]=a[1]+a[2]-a3>>1; 22 x[2]=a[1]-a[2]+a3>>1; 23 x[3]=-a[1]+a[2]+a3>>1; 24 if(x[1]<0||x[2]<0||x[3]<0)return; 25 s.erase(s.find(a[1])); 26 s.erase(s.find(a[2])); 27 s.erase(s.find(a3)); 28 for(int i=4;i<=n;i++) 29 { 30 x[i]=*s.begin()-x[1]; 31 if(x[i]<0)return; 32 for(int j=1;j<i;j++) 33 { 34 int t=x[j]+x[i]; 35 if(s.find(t)==s.end())return; 36 s.erase(s.find(t)); 37 } 38 } 39 for(int i=2;i<=n;i++) 40 if(x[i]<=x[i-1])return; 41 for(int i=1;i<=n;i++) 42 ans[tot][i]=x[i]; 43 tot++; 44 } 45 int main() 46 { 47 n=read(); 48 for(int i=1;i<=n*(n-1)/2;i++)a[i]=read(); 49 sort(a+1,a+n*(n-1)/2+1); 50 for(int i=3;i<=n;i++) 51 if(i==3||a[i]!=a[i-1]) 52 solve(a[i]); 53 printf("%d\n",tot); 54 for(int j=0;j<tot;j++,puts("")) 55 for(int i=1;i<=n;i++) 56 printf("%d ",ans[j][i]); 57 }
(PS:我发现有很多人特别快,不知道是怎么做的。。)
以上是关于[BZOJ2797][Poi2012]Squarks的主要内容,如果未能解决你的问题,请参考以下文章