洛谷P4774 [NOI2018]屠龙勇士

传送门

 

题解

这题到底是什么东西……数学题太珂怕了……

 1 //minamoto
 2 #include<iostream>
 3 #include<cstdio>
 4 #include<algorithm>
 5 #include<set>
 6 #define ll long long
 7 #define GG {puts("-1");return;}
 8 using namespace std;
 9 const int N=1e5+5;
10 #define getc() (p1==p2&&(p2=(p1=buf)+fread(buf,1,1<<21,stdin),p1==p2)?EOF:*p1++)
11 char buf[1<<21],*p1=buf,*p2=buf;
12 template<class T>inline bool cmax(T&a,const T&b){return a<b?a=b,1:0;}
13 inline ll read(){
14     #define num ch-'0'
15     char ch;bool flag=0;ll res;
16     while((ch=getc())>'9'||ch<'0')
17     (ch=='-')&&(flag=true);
18     for(res=num;(ch=getc())<='9'&&ch>='0';res=res*10+num);
19     (flag)&&(res=-res);
20     #undef num
21     return res;
22 }
23 multiset<ll> s;int n,m;ll mod[N],xs[N],cs[N],st[N],gif[N];int T;
24 inline void exgcd(ll a,ll &x,ll b,ll &y){
25     if(!b) return (void)(x=1,y=0);
26     exgcd(b,x,a%b,y);ll t=x;x=y,y=t-(a/b)*y;
27 }
28 inline ll gcd(ll a,ll b){
29     if(a<b) swap(a,b);
30     while(b^=a^=b^=a%=b);return a;
31 }
32 inline ll inv(ll a,ll p){a%=p;ll x,y;exgcd(a,x,p,y);return x<0?x+p:x;}
33 inline ll mul(ll a,ll b,const ll &mod){
34     ll res=0;b%=mod,b=b>0?b:b+mod;
35     for(;b;b>>=1,a=(a+a)%mod) (res+=a*(b&1))%=mod;
36     return res;
37 }
38 inline void spj(){
39     ll res=0;
40     for(int i=1;i<=n;++i) cmax(res,(cs[i]+xs[i]-1)/xs[i]);
41     printf("%lld\n",res);
42 }
43 inline void spj2(){
44     ll lc=1;
45     for(int i=1;i<=n;++i){
46         ll ds=mod[i]/gcd(mod[i],xs[i]);
47         lc=lc/gcd(lc,ds)*ds;
48     }
49     printf("%lld\n",lc);
50 }
51 void solve(){
52     n=read(),m=read();
53     for(int i=1;i<=n;++i) cs[i]=read();
54     for(int i=1;i<=n;++i) mod[i]=read();
55     for(int i=1;i<=n;++i) gif[i]=read();
56     for(int i=1;i<=m;++i) st[i]=read();
57     for(int i=1;i<=m;++i) s.insert(st[i]);
58     multiset<ll>::iterator ii;
59     for(int i=1;i<=n;++i){
60         ii=(cs[i]<(*s.begin()))?s.begin():(--s.upper_bound(cs[i]));
61         xs[i]=*ii,s.erase(ii),s.insert(gif[i]);
62     }
63     for(int i=1;i<=m;++i)
64     if(mod[i]==cs[i]){spj2();return;}
65     for(int i=1;i<=n;++i)
66     if(mod[i]==1){spj();return;}
67     for(int i=1;i<=n;++i) xs[i]%=mod[i];
68     for(int i=1;i<=n;++i)
69     if(xs[i]==0){
70         if(mod[i]==cs[i]) xs[i]=1,mod[i]=1,cs[i]=0;
71         else GG;
72     }
73     for(int i=1;i<=n;++i){
74         ll sx,sy,g=gcd(xs[i],mod[i]);
75         if(cs[i]%g!=0) GG;
76         exgcd(xs[i],sx,mod[i],sy);
77         mod[i]=mod[i]/g;sx=(sx%mod[i]+mod[i])%mod[i],cs[i]=mul(sx,cs[i]/g,mod[i]);
78     }
79     for(int i=1;i<n;++i){
80         ll g=gcd(mod[i],mod[i+1]);if((cs[i+1]-cs[i])%g!=0) GG;
81         ll ncs=mul(inv(mod[i]/g,mod[i+1]/g),(cs[i+1]-cs[i])/g,mod[i+1]/g);
82         ll nmod=mod[i]/g*mod[i+1];
83         ncs=mul(ncs,mod[i],nmod),(ncs+=cs[i])%=nmod,cs[i+1]=ncs,mod[i+1]=nmod;
84     }printf("%lld\n",cs[n]);
85 }
86 inline void clear(){s.clear();}
87 int main(){
88 //    freopen("testdata.in","r",stdin);
89     T=read();
90     for(int i=1;i<=T;++i) solve(),clear();
91     return 0;
92 }

 

posted @ 2018-09-30 14:58  bztMinamoto  阅读(279)  评论(0编辑  收藏  举报
Live2D