版权声明:虽然本蒟蒻很菜,但各位dalao转载请注明出处谢谢。 https://blog.csdn.net/xuxiayang/article/details/86682967
给出 个数,从中选出三个可以构成三角形三边的数(尽量靠前),回答 次询问(带单点修改!)
对于10%的数据,
对于30%的数据,
对于50%的数据,
对于100%的数据,
对于100%的数据,
比较容易想到 的暴力三重循环,然后加上最优化剪枝,我们假象一下出题人会怎样卡你
因为你打的是暴力,所以你的修改自然是 的,如果出题人想卡,他必然会卡你查询这一部分。
既然要卡查询,由于你找到一组最优解就退出了,所以他会让最优解尽量靠后。
可是如果尽量靠后,他数据最小也就是酱紫的:
1,1,2,3,5,8,13,21……
发现了吗?对!就是斐波那契数列!
而
是显然大于
的,也就是说答案最多是在前五十个数中,既然如此,暴力自然就可以水过咯
思考:
若
加强到
,该怎么做呢?
回答:
插入排序,
回答询问,也可以用
,这样就是
了
#pragma GCC optimize(2)
#include<cstdio>
#include<cctype>
#include<algorithm>
#define r(i,a,b) for(register int i=a;i<=b;i++)
#define d(i,a,b) for(register int i=a;i>=b;i--)
using namespace std;int n,a[100001],m,opt,x,y;
bool ok=false;
inline char Getchar()
{
static char buf[10000000],*p1=buf+10000000,*pend=buf+10000000;
if(p1==pend)
{
p1=buf; pend=buf+fread(buf,1,10000000,stdin);
if (pend==p1) return -1;
}
return *p1++;
}
inline long long read()
{
char c;int d=1;long long f=0;
while(c=Getchar(),!isdigit(c))if(c==45)d=-1;f=(f<<3)+(f<<1)+c-48;
while(c=Getchar(),isdigit(c)) f=(f<<3)+(f<<1)+c-48;
return d*f;
}
signed main()
{
n=read();
for(register int i=1;i<=n;i++) a[i]=read();
m=read();
while(m--)
{
opt=read();
if(opt==1) {x=read();y=read();a[x]=y;}
else
{
ok=false;
r(i,3,n)
{
if(ok) break;
r(j,1,i-1)
{
if(ok) break;
r(k,1,j-1)
if(a[i]+a[j]>a[k]&&a[i]+a[k]>a[j]&&a[k]+a[j]>a[i])
{
if(a[i]<=a[j])
{
if(a[i]<=a[k])
{
if(a[j]<=a[k]) printf("%d %d %d\n",a[i],a[j],a[k]);
else printf("%d %d %d\n",a[i],a[k],a[j]);
}
else printf("%d %d %d\n",a[k],a[i],a[j]);
}
else
{
if(a[i]>a[k])
{
if(a[j]>a[k]) printf("%d %d %d\n",a[k],a[j],a[i]);
else printf("%d %d %d\n",a[j],a[k],a[i]);
}
else printf("%d %d %d\n",a[j],a[i],a[k]);
}
ok=true;
break;
}
}
}
if(!ok) puts("-1 -1 -1");
}
}
}