感谢队内第二土豪gt大爷的代码的思路。
取两次及以上的lcm一定能在最优的情况下取得最大值,取0次lcm一定最后得到的都是最小的指数,取1次lcm的话需要判断到底哪个更优,取一下对数判断一下大小(取对数得到 a + log(2) 3 * b),sort一下就可以了。
#include <bits/stdc++.h>
#define INF 0x3f3f3f3f
using namespace std;
const int maxn = 50000+10;
int n ;
int s1[maxn],s2[maxn];
struct Power
{
int a,b;
}s[maxn];
bool cmp(Power t1 ,Power t2){return t1.a + log2(3) * t1.b < t2.a + log2(3) * t2.b;}
int main()
{
while(cin >> n)
{
int max1 = -INF,max2 = -INF,min1 = INF,min2 = INF;
for(int i = 0 ; i < n ; i++)
{
cin >> s1[i] >> s2[i];
s[i].a = s1[i] ,s[i].b = s2[i];
max1 = max(s1[i],max1);
max2 = max(s2[i],max2);
min1 = min(s1[i],min1);
min2 = min(s2[i],min2);
}
if(n == 1){printf("%d %d %d %d\n",max1,max2,min1,min2);}
else if(n == 2)
{
printf("%d %d %d %d\n",max1,max2,max1,max2);
printf("%d %d %d %d\n",min1,min2,min1,min2);
}
else if(n > 2)
{
int x1,x2,c1,c2;
sort(s,s+n,cmp);
printf("%d %d %d %d\n",max1,max2,max1,max2); // 全lcm
for(int i = 1 ; i < n-1 ;i++)
{
if(i == 1){c1 = s[0].a; c2 = s[0].b;} // 只有一次gcd
else{c1 = min1 ; c2 = min2;} // 多次gcd
if(1 == n-1-i){x1 = s[n-1].a ; x2 = s[n-1].b;} // 只有一次lcm
else{x1 = max1 ,x2 = max2;} // 多次lcm
printf("%d %d %d %d\n",x1,x2,c1,c2);
}
printf("%d %d %d %d\n",min1,min2,min1,min2);
}
}
return 0;
}