该题和挑战上一道题很类似,如果枚举四个值的话,复杂度太高。 那么我们可以想办法将复杂度分开。
方法是: 先用O(n^2)预处理出来a+b,然后枚举c和d,二分查找ab中有没有恰好等于d - c的值。
细节参见代码:
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const ll INF = 1000000000;
const int maxn = 2000+5;
int n,m,a[maxn];
struct node{
int a,b,ab;
bool operator < (const node& rhs) const {
return ab < rhs.ab;
}
}ab[maxn*maxn];
int lower(node* A,int x,int y,int v) {
int m ;
while(x < y) {
m = x + (y - x)/2;
if(A[m].ab >= v) y = m;
else x = m + 1;
}
return x;
}
int main() {
while(~scanf("%d",&n)&&n) {
int cnt = 0;
for(int i=0;i<n;i++) scanf("%d",&a[i]);
sort(a,a+n);
for(int i=0;i<n;i++) {
for(int j=i+1;j<n;j++) {
ab[cnt].ab = a[i]+a[j];
ab[cnt].a = a[i]; ab[cnt++].b = a[j];
}
}
sort(ab,ab+cnt);
int ans = -1;
for(int i=0;i<n;i++) {
for(int j=0;j<i;j++) {
if(ans >= a[i]) break;
int v = a[i] - a[j];
int u = lower(ab,0,cnt-1,v);
if(ab[u].ab == v && ab[u].a != a[i] && ab[u].b != a[i] && ab[u].a != a[j] && ab[u].b != a[j]) ans = a[i];
}
}
if(ans != -1) printf("%d\n",ans);
else printf("no solution\n");
}
return 0;
}