zoukankan      html  css  js  c++  java
  • [bzoj5418]屠龙勇士

    很显然,每一步所选的剑和怪物都是确定的,可以先求出来(不用写平衡树,直接用multiset即可,注意删除要删指针,以下假设第i次攻击用ki攻击的剑,攻击第i只怪)
     首先判断无解,即如果存在ai使得gcd(ki,pi)不是ai的约数就无解,否则将ki、pi、ai同除gcd(ki,pi),并用扩欧求出ki关于pi的逆元,移到右边
    最终相当于求线性方程组的最小正整数解,用EXCRT即可
     1 #include<bits/stdc++.h>
     2 using namespace std;
     3 #define N 100005
     4 #define ll long long
     5 multiset<ll>s;
     6 multiset<ll>::iterator it;
     7 int T,n,m;
     8 ll x,y,sum,a[N],p[N],t[N];
     9 bool flag;
    10 ll exgcd(ll a,ll b,ll &x,ll &y){
    11     if (!b){
    12         x=1;
    13         y=0;
    14         return a;
    15     }
    16     ll t=exgcd(b,a%b,y,x);
    17     y-=a/b*x;
    18     return t;
    19 }
    20 ll mul(ll a,ll b,ll p){
    21     if (!b)return 0;
    22     ll s=mul(a,b>>1,p);
    23     s=s*2%p;
    24     if (b&1)s=(s+a)%p;
    25     return s;
    26 }
    27 int main(){
    28     scanf("%d",&T);
    29     while (T--){
    30         scanf("%d%d",&n,&m);
    31         for(int i=1;i<=n;i++)scanf("%lld",&a[i]);
    32         for(int i=1;i<=n;i++)scanf("%lld",&p[i]);
    33         for(int i=1;i<=n;i++)scanf("%lld",&t[i]);
    34         s.clear();
    35         for(int i=1;i<=m;i++){
    36             scanf("%lld",&x);
    37             s.insert(x);
    38         }
    39         for(int i=1;i<=n;i++){
    40             it=s.upper_bound(a[i]);
    41             if (it!=s.begin())it--;
    42             x=*it;
    43             s.erase(it);
    44             s.insert(t[i]);
    45             t[i]=x;
    46         }
    47         flag=sum=0;
    48         for(int i=1;i<=n;i++){
    49             sum=max(sum,(a[i]-1)/t[i]);
    50             ll d=exgcd(t[i],p[i],x,y);
    51             if (a[i]%d){
    52                 flag=1;
    53                 break;
    54             }
    55             p[i]/=d;
    56             a[i]=mul(a[i]/d,(x%p[i]+p[i])%p[i],p[i]);
    57         }
    58         for(int i=2;i<=n;i++){
    59             ll d=exgcd(p[1],p[i],x,y);
    60             if (a[1]%d!=a[i]%d){
    61                 flag=1;
    62                 break;
    63             }
    64             p[i]/=d;
    65             a[1]+=mul((a[i]-a[1])/d,(x%p[i]+p[i])%p[i],p[i])*p[1];
    66             p[1]*=p[i];
    67             a[1]=((a[1]%p[1])+p[1])%p[1];
    68         }
    69         if (flag)printf("-1\n");
    70         else
    71             if (sum<a[1])printf("%lld\n",a[1]);
    72             else printf("%lld\n",a[1]+(sum-a[1]+p[1])/p[1]*p[1]);
    73     }
    74 }
    View Code
  • 相关阅读:
    219. Contains Duplicate II
    189. Rotate Array
    169. Majority Element
    122. Best Time to Buy and Sell Stock II
    121. Best Time to Buy and Sell Stock
    119. Pascal's Triangle II
    118. Pascal's Triangle
    88. Merge Sorted Array
    53. Maximum Subarray
    CodeForces 359D Pair of Numbers (暴力)
  • 原文地址:https://www.cnblogs.com/PYWBKTDA/p/11516918.html
Copyright © 2011-2022 走看看