版权声明:http://blog.csdn.net/Mitsuha_。 https://blog.csdn.net/Mitsuha_/article/details/84761942
2018-2019 ICPC, NEERC, Northern Eurasia Finals
在此附上题解
Problem F:Fractions
思路:看懂题意之后,相当于求解
其中
。
这下不了手,然后发现很多数只需要2项即可凑出来,大胆猜了一发。
如果只有2项的话,则是
其中
,然后就是求
的正整数解了,用扩展欧几里德即可。
#include<bits/stdc++.h>
using namespace std;
const int MOD=1e9+7;
const int MAX=2e5+10;
const double PI=acos(-1.0);
typedef long long ll;
ll gcd(ll x,ll y){return y==0?x:gcd(y,x%y);}
void exgcd(ll a,ll b,ll &x,ll&y)
{
if(b==0){x=1;y=0;}
else
{
exgcd(b,a%b,y,x);
y-=x*(a/b);
}
}
int main()
{
ll n;
cin>>n;
for(ll i=2;i*i<=n;i++)
{
if(n%i==0)
{
ll a=i;
ll b=n/i;
ll g=gcd(a,b);
if((n-1)%g)continue;
ll x,y;
exgcd(a,b,x,y);
x=(x+b/g)*((n-1)/g);
x=(x%(b/g)+b/g)%(b/g);
y=(n-1-a*x)/b;
printf("YES\n2\n");
printf("%lld %lld\n",x/gcd(x,b),b/gcd(x,b));
printf("%lld %lld\n",y/gcd(y,a),a/gcd(y,a));
return 0;
}
}
puts("NO");
return 0;
}
Problem K:King Kog’s Reception
思路:对于一个区间 来说,假设这个区间内所有骑士的 的值加起来为 ,若 ,很明显,骑士最后结束见面的时间是会超出这个区间的,且超出的时间 。
那么对于每个询问
,我们就是要找到最大的
。
然后就需要用数据结构来维护
了。
#include<bits/stdc++.h>
using namespace std;
const int MOD=998244353;
const int MAX=1e6+10;
const double PI=acos(-1.0);
typedef long long ll;
int X[MAX],Y[MAX];
struct lenka
{
int l,r;
ll ma,tag;
}A[MAX<<2];
void build(int k,int l,int r)
{
A[k].l=l,A[k].r=r;
A[k].ma=l;
if(l==r)return;
build(2*k,l,(l+r)/2);
build(2*k+1,(l+r)/2+1,r);
A[k].ma=max(A[2*k].ma,A[2*k+1].ma);
}
void add(int k,int x,int y,ll z)
{
if(x==A[k].l&&y==A[k].r)
{
A[k].tag+=z;
A[k].ma+=z;
return;
}
if(A[k].tag)
{
add(2*k,A[2*k].l,A[2*k].r,A[k].tag);
add(2*k+1,A[2*k+1].l,A[2*k+1].r,A[k].tag);
A[k].tag=0;
}
if(y<=A[2*k].r)add(2*k,x,y,z);
else if(x>=A[2*k+1].l)add(2*k+1,x,y,z);
else
{
add(2*k,x,A[2*k].r,z);
add(2*k+1,A[2*k+1].l,y,z);
}
A[k].ma=max(A[2*k].ma,A[2*k+1].ma);
}
ll askma(int k,int x,int y)
{
if(x==A[k].l&&y==A[k].r)return A[k].ma;
if(A[k].tag)
{
add(2*k,A[2*k].l,A[2*k].r,A[k].tag);
add(2*k+1,A[2*k+1].l,A[2*k+1].r,A[k].tag);
A[k].tag=0;
}
if(y<=A[2*k].r)return askma(2*k,x,y);
if(x>=A[2*k+1].l)return askma(2*k+1,x,y);
return max(askma(2*k,x,A[2*k].r),askma(2*k+1,A[2*k+1].l,y));
}
ll BIT[MAX];
void add(int x,int y){while(x<=1000000){BIT[x]+=y;x+=x&(-x);}}
ll ask(int x){ll tot=0;while(x){tot+=BIT[x];x-=x&(-x);}return tot;}
int main()
{
build(1,1,1000000);
int T;
cin>>T;
for(int i=1;i<=T;i++)
{
char s[4];
scanf("%s",s);
if(s[0]=='+')
{
scanf("%d%d",&X[i],&Y[i]);
add(1,1,X[i],Y[i]);
add(X[i],Y[i]);
}
if(s[0]=='-')
{
scanf("%d",&X[i]);
add(1,1,X[X[i]],-Y[X[i]]);
add(X[X[i]],-Y[X[i]]);
}
if(s[0]=='?')
{
scanf("%d",&X[i]);
printf("%lld\n",askma(1,1,X[i])-X[i]-(ask(1000000)-ask(X[i])));
}
}
return 0;
}