BZOJ5394: [Ynoi2016]炸脖龙(欧拉广义降幂)
就是让你求这个:

传送门:https://www.lydsy.com/JudgeOnline/problem.php?id=5394
解题思路:
NOIP2018后第一道题,感觉非常像那个上帝与集合的正确用法。
具体来说就是使用递归的求解方式,不过这次和上帝与集合的正确用法不同的是:
1.这次不是无限项,所以可以不在p=0时停止。
2.因为被取模数有限大,所以要特判小于φ(p)的情况。
3.询问时要预先处理φ(p)
代码:
#include<cstdio>
#include<cstring>
#include<algorithm>
#define lll spc<<1
#define rrr spc<<1|1
#define maxval 20000000
typedef long long lnt;
struct trnt{
lnt val;
lnt lzt;
}tr[];
int prime[];
int eula[];
bool vis[];
int cnt;
int n,m;
lnt a[];
lnt read(void)
{
lnt ans=;
lnt f=;
char ch=getchar();
while(ch<''||ch>'')
{
if(ch=='-')
f=-f;
ch=getchar();
}
while(ch<=''&&ch>='')
{
ans=ans*10ll+(lnt)(ch-'');
ch=getchar();
}
return ans*f;
}
void Get_prime(void)
{
for(int i=;i<=maxval;i++)
{
if(!vis[i])
{
prime[++cnt]=i;
eula[i]=i-;
}
vis[i]=false;
for(int j=;j<=cnt&&(i*prime[j]<=maxval);j++)
{
vis[i*prime[j]]=true;
if(i%prime[j]==)
{
eula[i*prime[j]]=eula[i]*prime[j];
break;
}
eula[i*prime[j]]=eula[i]*(prime[j]-);
}
}
return ;
}
void Add(int spc,int l,int r,lnt v)
{
tr[spc].val+=v*(lnt)(r-l+);
tr[spc].lzt+=v;
return ;
}
void pushup(int spc)
{
tr[spc].val=tr[lll].val+tr[rrr].val;
return ;
}
void pushdown(int spc,int l,int r)
{
if(tr[spc].lzt)
{
int mid=(l+r)>>;
Add(lll,l,mid,tr[spc].lzt);
Add(rrr,mid+,r,tr[spc].lzt);
tr[spc].lzt=;
}
return ;
}
void build(int l,int r,int spc)
{
if(l==r)
{
tr[spc].val=a[l];
return ;
}
int mid=(l+r)>>;
build(l,mid,lll);
build(mid+,r,rrr);
pushup(spc);
return ;
}
void update(int l,int r,int ll,int rr,int spc,lnt v)
{
if(ll>r||l>rr)
return ;
if(ll<=l&&r<=rr)
{
Add(spc,l,r,v);
return ;
}
int mid=(l+r)>>;
pushdown(spc,l,r);
update(l,mid,ll,rr,lll,v);
update(mid+,r,ll,rr,rrr,v);
pushup(spc);
return ;
}
lnt query(int l,int r,int spc,int pos)
{
if(l==r)
return tr[spc].val;
int mid=(l+r)>>;
pushdown(spc,l,r);
if(pos<=mid)
return query(l,mid,lll,pos);
return query(mid+,r,rrr,pos);
}
lnt ksm(lnt a,lnt b,lnt mod,int plc)
{
lnt ans=;
while(b)
{
if(b&)
{
ans=ans*a;
if(ans>=mod)
{
ans%=mod;
vis[plc]=true;
}
}
a=a*a;
if(a>=mod)
{
a%=mod;
vis[plc]=true;
}
b/=;
}
return ans;
}
lnt Query(int l,int r,int p)
{
vis[l]=false;
lnt tmp=query(,n,,l);
if(tmp>=p)
vis[l]=true;
tmp%=p;
if(tmp==)
return ;
if(p==)
return ;
if(l==r)
return tmp%p;
lnt temp=eula[p];
return ksm(tmp,Query(l+,r,temp)+vis[l+]*temp,p,l);
}
int main()
{
Get_prime();
n=read();
m=read();
for(int i=;i<=n;i++)
a[i]=read();
build(,n,);
while(m--)
{
lnt cmd=read(),l=read(),r=read(),x=read();
if(cmd==)
update(,n,l,r,,x);
else
printf("%lld\n",Query(l,r,x));
}
return ;
}
BZOJ5394: [Ynoi2016]炸脖龙(欧拉广义降幂)的更多相关文章
- [洛谷P4118][Ynoi2016]炸脖龙I([洛谷P3934]Nephren Ruq Insania)
题目大意:有$n$个数,每个数为$s_i$,两个操作: $1\;l\;r\;x:$表示将区间$[l,r]$内的数加上$x$ $2\;l\;r\;p:$表示求$s_l^{s_{l+1}^{^{s_{l+ ...
- BZOJ 5394 [Ynoi2016]炸脖龙 (线段树+拓展欧拉定理)
题目大意:给你一个序列,需要支持区间修改,以及查询一段区间$a_{i}^{a_{i+1}^{a_{i+2}...}}mod\;p$的值,每次询问的$p$的值不同 对于区间修改,由线段树完成,没什么好说 ...
- P4118 [Ynoi2016]炸脖龙I
思路:扩展欧拉定理 提交:\(\geq5\)次 错因:快速幂时刚开始没有判断\(a\)是否大于\(p\) 题解: 用树状数组维护差分,查询时暴力从左端点的第一个数向右端点递归,若递归时发现指数变为\( ...
- Luogu P4118 [Ynoi2016]炸脖龙I
题目 首先考虑没有修改的情况.显然直接暴力扩展欧拉定理就行了,单次复杂度为\(O(\log p)\)的. 现在有了修改,我们可以树状数组维护差分数组,然后\(O(\log n)\)地单次查询单点值. ...
- Uva 10129 - Play on Words 单词接龙 欧拉道路应用
跟Uva 10054很像,不过这题的单词是不能反向的,所以是有向图,判断欧拉道路. 关于欧拉道路(from Titanium大神): 判断有向图是否有欧拉路 1.判断有向图的基图(即有向图转化为无向图 ...
- FZU 1759 欧拉函数 降幂公式
Description Given A,B,C, You should quickly calculate the result of A^B mod C. (1<=A,C<=1000 ...
- HDU 3221 矩阵快速幂+欧拉函数+降幂公式降幂
装载自:http://www.cnblogs.com/183zyz/archive/2012/05/11/2495401.html 题目让求一个函数调用了多少次.公式比较好推.f[n] = f[n-1 ...
- FZU Super A^B mod C(欧拉函数降幂)
Problem 1759 Super A^B mod C Accept: 878 Submit: 2870 Time Limit: 1000 mSec Memory Limit : 327 ...
- ACM-数论-广义欧拉降幂
https://www.cnblogs.com/31415926535x/p/11447033.html 曾今一时的懒,造就今日的泪 记得半年前去武大参加的省赛,当时的A题就是一个广义欧拉降幂的板子题 ...
随机推荐
- 计数排序、桶排序python实现
计数排序在输入n个0到k之间的整数时,时间复杂度最好情况下为O(n+k),最坏情况下为O(n+k),平均情况为O(n+k),空间复杂度为O(n+k),计数排序是稳定的排序. 桶排序在输入N个数据有M个 ...
- AES加密解密在JAVA和ANDROID下互通
<span style="font-family: Arial, Helvetica, sans-serif;">昨天外包安卓的那个人说AES的加解密结果不一样.于是百 ...
- 无法往SQL Server Management Studio拖脚本
解决方法:不要用Administrator权限打开sql server
- jquery easyui 输入框 禁止输入负数 设置属性data-options="min:0,required:true"
jquery easyui 输入框 禁止输入负数 设置属性data-options="min:0,required:true" <input id="days& ...
- Python正则表达式初识(八)
继续分享Python正则表达式的基础知识,今天给大家分享的特殊字符是“\w”和“\W”,具体的教程如下. 1.“\w”代表的意思是该字符为任意字符,但是和特殊字符“.”的意思不同.“\w”代表的字符主 ...
- Java基础String的方法
Java基础String的方法 字符串类型写法格式如下: 格式一: String 变量名称; 变量名称=赋值(自定义或传入的变量值); 格式二: String 变量名称=赋值(自定义或传入的变量值); ...
- tac---反转输出文件
tac命令用于将文件已行为单位的反序输出,即第一行最后显示,最后一行先显示.
- Centos6.5 安装lnmp环境
最近项目要配置在nginx上,所以搜索了下具体nginx的安装,看到这篇文章简洁明了而且测试成功就借用了,作品出处:http://www.cnblogs.com/xiaoit/p/3991037.ht ...
- CodeForcesGym 100502G Outing
Outing Time Limit: 1000ms Memory Limit: 524288KB This problem will be judged on CodeForcesGym. Origi ...
- JAVA学习第五十四课 — IO流(八)打印流 & 序列流
一.综合练习-文件清单列表 获取指定文件夹下,指定扩展名的文件(含子文件夹),并将这些文件的绝对路径写到一个文本文件里.也就是建立一个指定扩展名的文件列表 1.深度遍历 2.过滤器->容器 3. ...