题目链接:

[Noi2018]屠龙勇士

题目大意:有$n$条龙和初始$m$个武器,每个武器有一个攻击力$t_{i}$,每条龙有一个初始血量$a_{i}$和一个回复值$p_{i}$(即只要血量为负数就一直回复$p_{i}$的血量,只有在攻击后会回血),杀死一条龙当且仅当攻击结束后或回复血量之后血量为$0$,杀死一条龙会获得一个新的武器。现在要求对每条龙攻击固定次数$x$求出最小的$x$,使所有龙都能被杀死。

因为每次选择的武器是固定的,所以只要用$multiset$存当前剩下的武器然后每次按题目规则取即可。设攻击第$i$条龙的武器攻击力为$ti$,那么可以得到$n$个不定方程$x*t_{i}-k*p_{i}=a_{i}$。对于每个不定方程因为$p_{i}$与$t_{i}$不一定互质,所以求出$d=gcd(p_{i},t_{i})$并将等式两边都除掉$d$(如果$a_{i}$不能整除$d$则无解)。这样每个方程就能用$exgcd$解出最小的非负整数解$x_{i}$,那么显然$x\equiv x_{i}(mod\ \frac{p_{i}}{d})$。由此得到了$n$个方程的同余方程组(设每个同余方程的模数为$m_{i}$,即为上面的$\frac{p_{i}}{d}$),由于模数不一定互质,所以要用扩展CRT来求出最小的$x$。因为要保证攻击能将每条龙打到至少$0$血,即$x*t_{i}>=a_{i}$,所以要求出将每条龙打到$0$血或往下的最小次数的最大值$mx$,只要$x$小于$mx$就不停地给$x$加上$lcm(m_{1},m_{2}...m_{n})$。

#include<set>
#include<map>
#include<queue>
#include<stack>
#include<cmath>
#include<cstdio>
#include<vector>
#include<bitset>
#include<cstring>
#include<iostream>
#include<algorithm>
#define ll long long
#define INF 4e18+10
using namespace std;
ll c1,m1,c2,m2;
int N,M,T;
ll mx,x;
ll lcm;
multiset<ll>s;
multiset<ll>::iterator it;
ll a[100010];
ll p[100010];
ll b[100010];
ll t[100010];
ll c[100010];
ll m[100010];
ll quick(ll x,ll y,ll mod)
{
ll res=0ll;
while(y)
{
if(y&1)
{
res=(res+x)%mod;
}
y>>=1;
x=(x+x)%mod;
}
return res;
}
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)
{
x=1;y=0;
return ;
}
exgcd(b,a%b,y,x);
y-=(a/b)*x;
}
ll inv(ll n,ll mod)
{
ll x,y;
exgcd(n,mod,x,y);
return (x%mod+mod)%mod;
}
int main()
{
scanf("%d",&T);
while(T--)
{
scanf("%d%d",&N,&M);
s.clear();
mx=0;
for(int i=1;i<=N;i++)
{
scanf("%lld",&a[i]);
}
for(int i=1;i<=N;i++)
{
scanf("%lld",&p[i]);
}
for(int i=1;i<=N;i++)
{
scanf("%lld",&t[i]);
}
for(int i=1;i<=M;i++)
{
scanf("%lld",&x);
s.insert(x);
}
for(int i=1;i<=N;i++)
{
it=s.upper_bound(a[i]);
if(it!=s.begin())
{
it--;
}
b[i]=*it;
s.erase(it);
s.insert(t[i]);
}
bool flag=false;
for(int i=1;i<=N;i++)
{
mx=max(mx,(a[i]-1)/b[i]+1);
ll d=gcd(b[i],p[i]);
if(a[i]%d)
{
flag=true;
break;
}
ll x,y;
exgcd(b[i]/d,p[i]/d,x,y);
ll P=p[i]/d;
x=quick(x,a[i]/d,P);
x=(x%P+P)%P;
c[i]=x;
m[i]=P;
}
if(flag)
{
printf("-1\n");
continue;
}
flag=false;
m1=m[1],c1=c[1];
for(int i=2;i<=N;i++)
{
c2=c[i],m2=m[i];
ll d=gcd(m1,m2);
if((c2-c1)%d)
{
flag=true;
break;
}
ll g=inv(m1/d,m2/d);
ll sum=quick((c2-c1)/d,g,m2/d);
ll mod=quick(m1,m2/d,INF);
sum=quick(sum,m1,mod);
sum+=c1,sum%=mod;
c1=sum,m1=mod;
}
if(flag)
{
printf("-1\n");
continue;
}
c1=(c1%m1+m1)%m1;
ll ans=1ll;
for(int i=1;i<=N;i++)
{
ll d=gcd(ans,m[i]);
ans=quick(ans/d,m[i],INF);
}
if(c1>=mx)
{
printf("%lld\n",c1);
continue;
}
ll res=ceil((double)(mx-c1)/ans);
c1+=quick(ans,res,INF);
printf("%lld\n",c1);
}
}

BZOJ5418[Noi2018]屠龙勇士——exgcd+扩展CRT+set的更多相关文章

  1. NOI2018屠龙勇士(扩展CRT + splay(multiset))

    QWQ 一到假期就颓废 哎 今年新鲜出炉的NOI题,QwQ同步赛的时候写的,后来交了一发洛谷,竟然过了 首先 根据题目,我们很容易得到,假设对应每一条龙的剑的攻击力是\(atk\)的话 \[a_i-x ...

  2. 洛谷P4774 BZOJ5418 LOJ2721 [NOI2018]屠龙勇士(扩展中国剩余定理)

    题目链接: 洛谷 BZOJ LOJ 题目大意:这么长的题面,就饶了我吧emmm 这题第一眼看上去没法列出同余方程组.为什么?好像不知道用哪把剑杀哪条龙…… 仔细一看,要按顺序杀龙,所以获得的剑出现的顺 ...

  3. BZOJ5418:[NOI2018]屠龙勇士(exCRT,exgcd,set)

    Description Input Output Sample Input 23 33 5 74 6 107 3 91 9 10003 23 5 64 8 71 1 11 1 Sample Outpu ...

  4. LOJ2721 [NOI2018] 屠龙勇士 【扩展中国剩余定理】

    好久没写了,写一篇凑个数. 题目分析: 这题不难想,讲一下中国剩余定理怎么扩展. 考虑$$\left\{\begin{matrix}x \equiv a\pmod{b}\\ x \equiv c\pm ...

  5. BZOJ5418 NOI2018屠龙勇士(excrt)

    显然multiset求出每次用哪把剑.注意到除了p=1的情况,其他数据都保证了ai<pi,于是先特判一下p=1.比较坑的是还可能存在ai=pi,稍微考虑一下. 剩下的部分即解bix≡ai(mod ...

  6. BZOJ_5418_[Noi2018]屠龙勇士_exgcd+excrt

    BZOJ_5418_[Noi2018]屠龙勇士_exgcd+excrt Description www.lydsy.com/JudgeOnline/upload/noi2018day2.pdf 每次用 ...

  7. P4774 [NOI2018]屠龙勇士

    P4774 [NOI2018]屠龙勇士 先平衡树跑出打每条龙的atk t[] 然后每条龙有\(xt \equiv a[i](\text{mod }p[i])\) 就是\(xt+kp[i]=a[i]\) ...

  8. [洛谷P4774] [NOI2018]屠龙勇士

    洛谷题目链接:[NOI2018]屠龙勇士 因为markdown复制过来有点炸格式,所以看题目请戳上面. 题解: 因为杀死一条龙的条件是在攻击\(x\)次,龙恢复\(y\)次血量\((y\in N^{* ...

  9. uoj396 [NOI2018]屠龙勇士

    [NOI2018]屠龙勇士 描述 小 D 最近在网上发现了一款小游戏.游戏的规则如下: 游戏的目标是按照编号 1∼n 顺序杀掉 n 条巨龙,每条巨龙拥有一个初始的生命值 ai .同时每条巨龙拥有恢复能 ...

随机推荐

  1. FineUI经典项目展示(1)生产在线管理系统

    本系列<FineUI经典项目展示>文章将会集中展示一批使用FineUI(开源版).专业版.MVC版的经典项目. 如果你希望自己的FineUI项目出现在这个舞台,请到官网论坛提交申请: ht ...

  2. C#.NET 大型通用信息化系统集成快速开发平台 4.1 版本 - 严格的用户账户审核功能

    整个集团有几万个用户,一个个用户添加是不现实的,只有每个公司的系统管理员添加.或者用户申请帐户,然后有相应的管理员审核,才会更准确一些. 每个公司.分公司.部门的账户情况只有所在公司的管理员是最清楚的 ...

  3. nodeJs配置

    1.  vi /etc/profile export NODE_HOME=/opt/node-v6.9.1-linux-x64export PATH=$PATH:$NODE_HOME/binexpor ...

  4. SQLServer 存储过程+定时任务发邮件

    SQLServer 代理发邮件需要开启SQL Server 代理服务器,然后,在[管理]-[数据库邮件]中,右键点击配置数据库邮件. 我用的是腾讯的企业邮箱,个人的163邮箱略微不同.下图是相关邮件的 ...

  5. Linux登录MySQL时出现 Can't connect to local MySQL server through socket '/tmp/mysql.sock'解决方法

    在Linux上登录MySQL时出现如下提示,如下图: 通过查找资料了解到: MySQL有两种连接方式: (1)TCP/IP (2)socket 对mysql.sock来说,其作用是程序与mysqlse ...

  6. Codeforces Round #534 (Div. 2)D. Game with modulo-1104-D(交互+二分+构造)

    D. Game with modulo time limit per test 1 second memory limit per test 256 megabytes input standard ...

  7. ModelAttribute用法之一

    @ModelAttribute也可以做为Model输出到View时使用,比如: 测试例子   package com.my.controller; import java.util.ArrayList ...

  8. (关于数据传输安全)SSH协议

    这里说的不是java的SSH框架,是1995年,芬兰学者Tatu Ylonen设计的SSH协议. 有计算机网络基础的同学都知道,在网上传输的数据是可以被截取的.那么怎样才能获得安全? 一.春点行话 电 ...

  9. Python之加密模块

    hashlib模块 加密方式以md5方式加密举例 是标准模块,直接导入即可 还有其他的加密方式,比如:.sha1()..sha224()..sha256()等,加密后的字符串长度更长,安全性更高 一. ...

  10. C#复习笔记(4)--C#3:革新写代码的方式(扩展方法)

    扩展方法 扩展方法有以下几个需求: 你想为一个类型添加一些 成员: 你不需要为类型的实例添加任何更多的数据: 你不能改变类型本身, 因为是别人的代码. 对于C#1和C#2中的静态方法,扩展方法是一种更 ...