Portal --> loj6059

Solution

​​  看过去第一反应是。。大力数位dp!然后看了一眼数据范围。。。

​  但是这没有什么关系!注意到我们不需要考虑前导零了,可以直接快乐dp

​  状态还是能继续用的,记\(f[i][j][k]\)表示从左往右数的前\(i\)位,(假装后面没有数位的情况下)模\(p\)余\(j\),数字和为\(k\)

​  然后。。\(n\)特别大所以我们考虑。。倍增求解,考虑从\(\lfloor\frac{i}{2}\rfloor\)转移到\(i\):

\[f[\lfloor\frac{i}{2}\rfloor][x][j]*f[\lfloor\frac{i}{2}\rfloor][y][k]\rightarrow f[i][x+y][(j+10^w*k)\%p]
\]

​  这个\(w\)的话就是。。\(\lfloor\frac{i}{2}\rfloor\)

​​  但是如果说\(i\)是奇数怎么办呢?其实只要在这样转移完了之后再暴力枚举一下最高位是啥就好了(现在是相当于得到了一个\(i-1\)位的数嘛)

​​  然后发现因为\(p\)和\(m\)都比较小,所以我们可以直接枚举,而第二维的那个\(f[][x][j]*f[][y][k]\rightarrow f[][x+y][]\)的是一个卷积的形式,我们可以用NTT来优化

​​  具体的话其实感觉跟这题的处理有点像【Portal -->Lcm】,也是我们先将\(f[i][x]\)DFT(NTT)一下之后就可以随便搞事了,也就是相当于第二维和第三维在某种意义上独立了,然后我们可以将转移分开处理(先搞第二维的转移,再暴力枚举第三维的转移)

​  至于倍增的话。。递归就好了,边界的话就是\(i=0\)的情况

​​  因为中间要快乐NTT所以一定要记得相关数组清空

​  

​​  代码大概长这个样子

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
const int MOD=998244353,N=3010,M=3010,NT=N*4,TOP=11,G=3;
int f[N][M],g[N][M];
int n,m,p,ans;
int mul(int x,int y){return 1LL*x*y%MOD;}
int add(int x,int y){return (1LL*x+y)%MOD;}
int ksm(int x,int y){
int ret=1,base=x;
for (;y;y>>=1,base=mul(base,base))
if (y&1) ret=mul(ret,base);
return ret;
}
namespace NTT{/*{{{*/
int A[NT],B[NT],W[NT][2],rev[NT];
int len,invlen,invg;
void get_len(int n,int m){
for (int i=0;i<len;++i) A[i]=B[i]=0;
int bit=0;
for (len=1;len<=n+m;len<<=1,++bit);
rev[0]=0;
for (int i=1;i<len;++i) rev[i]=(rev[i>>1]>>1)|((i&1)<<(bit-1));
invlen=ksm(len,MOD-2);
}
void init(int n){
invg=ksm(G,MOD-2);
for (int i=1;i<=TOP;++i){
W[1<<i][0]=ksm(G,(MOD-1)/(1<<i));
W[1<<i][1]=ksm(invg,(MOD-1)/(1<<i));
}
get_len(n,n);
}
void ntt(int *a,int op){
int w,w_n,u,v;
for (int i=0;i<len;++i) if (rev[i]>i) swap(a[i],a[rev[i]]);
for (int step=2;step<=len;step<<=1){
w_n=W[step][op==-1];
for (int st=0;st<len;st+=step){
w=1;
for (int i=0;i<(step>>1);++i){
v=mul(a[st+i+(step>>1)],w);
u=a[st+i];
a[st+i]=add(u,v);
a[st+i+(step>>1)]=add(u,MOD-v);
w=mul(w,w_n);
}
}
}
if (op==1) return;
for (int i=0;i<len;++i) a[i]=mul(a[i],invlen);
}
}/*}}}*/
int work(int n){
if (!n) return 1;
int mi=work(n>>1);
for (int i=0;i<p;++i)
NTT::ntt(g[i],1);
for (int i=0;i<p;++i)
for (int j=0;j<p;++j)
for (int k=0;k<NTT::len;++k)
f[(i+j*mi%p)%p][k]=add(f[(i+j*mi%p)%p][k],mul(g[i][k],g[j][k]));
for (int i=0;i<p;++i)
for (int j=0;j<NTT::len;++j)
g[i][j]=0;
for (int i=0;i<p;++i){
NTT::ntt(f[i],-1);
for (int j=0;j<m;++j) g[i][j]=f[i][j];
for (int j=0;j<NTT::len;++j) f[i][j]=0;
}
mi=mi*mi%p;
if (n&1){
for (int i=0;i<p;++i)
for (int x=0;x<10;++x)
for (int j=0;j+x<m;++j)
f[(i+x*mi%p)%p][j+x]=add(f[(i+x*mi%p)%p][j+x],g[i][j]);
for (int i=0;i<p;++i)
for (int j=0;j<m;++j)
g[i][j]=f[i][j],f[i][j]=0;
mi=mi*10%p;
}
return mi;
} int main(){
#ifndef ONLINE_JUDGE
freopen("a.in","r",stdin);
#endif
scanf("%d%d%d",&n,&p,&m);
g[0][0]=1; ++m;
NTT::init(m);
work(n);
ans=0;
for (int i=0;i<m;++i){
ans=add(ans,g[0][i]);
printf("%d ",ans);
}
}

【loj6059】Sum的更多相关文章

  1. 【BZOJ3944】Sum(杜教筛)

    [BZOJ3944]Sum(杜教筛) 题面 求\[\sum_{i=1}^n\mu(i)和\sum_{i=1}^n\phi(i)\] 范围:\(n<2^{31}\) 令\[S(n)=\sum_{i ...

  2. 【CF914G】Sum the Fibonacci 快速??变换模板

    [CF914G]Sum the Fibonacci 题解:给你一个长度为n的数组s.定义五元组(a,b,c,d,e)是合法的当且仅当: 1. $1\le a,b,c,d,e\le n$2. $(s_a ...

  3. 【BZOJ4262】Sum 单调栈+线段树

    [BZOJ4262]Sum Description Input 第一行一个数 t,表示询问组数. 第一行一个数 t,表示询问组数. 接下来 t 行,每行四个数 l_1, r_1, l_2, r_2. ...

  4. 【POJ1707】【伯努利数】Sum of powers

    Description A young schoolboy would like to calculate the sum for some fixed natural k and different ...

  5. 【leetcode】Sum Root to Leaf Numbers(hard)

    Given a binary tree containing digits from 0-9 only, each root-to-leaf path could represent a number ...

  6. 【LeetCode】Sum of Two Integers

    问题描述: Calculate the sum of two integers a and b, but you are not allowed to use the operator + and - ...

  7. 【POJ2739】Sum of Consecutive Prime Numbers

    简单的素数打表,然后枚举.开始没注意n读到0结束,TLE了回..下次再认真点.A过后讨论里面有个暴力打表过的,给跪了! #include <iostream> #include <c ...

  8. 【LeetCode】Sum Root to Leaf Numbers

    题目 Given a binary tree containing digits from 0-9 only, each root-to-leaf path could represent a num ...

  9. 【leetcode74】Sum of Two Integers(不用+,-求两数之和)

    题目描述: 不用+,-求两个数的和 原文描述: Calculate the sum of two integers a and b, but you are not allowed to use th ...

随机推荐

  1. HTTP 两种基本请求方法 GET和 POST的区别

    GET方法 1.GET交互方式是从服务器上获取数据,而并非修改数据,所以GET交互方式是安全的.就像数据库查询一样,从数据库查询数据,并不会影响数据库的数据信息,对数据库来说,也就是安全的.2.GET ...

  2. i3wm随笔 1

    快捷键 mod+0 退出 mod+v 垂直分割 mod+h 水平风格

  3. 《物质世界 (Outward)》证明不必压缩制作大型角色扮演游戏的时间

    <物质世界>是一款雄心勃勃的开放世界角色扮演游戏 (RPG),设计这款游戏的公司规模只有您预期的三分之一.游戏中的一切都是动态的,拥有许多炫酷的系统设计,大家可以分屏合作掌控整个场景.参与 ...

  4. linux ——使用find如何快速替换所有相同参数

    在生成环境上有时候需要大规模修改某一配置里的参数,但是该参数存在多个地方,比如IP地址 端口 项目名等,特别是项目名称混乱想统一 find  /项目地址 -type f |xargs grep &qu ...

  5. [T-ARA][Lovey-Dovey]

    歌词来源:http://music.163.com/#/song?id=22704426 作曲 : 新沙洞老虎/崔圭成 [作曲 : 新沙洞老虎/崔圭成] [作曲 : 新沙洞老虎/崔圭成] 作词 : 新 ...

  6. 15 分钟用 ML 破解一个验证码系统

    人人都恨验证码——那些恼人的图片,显示着你在登陆某网站前得输入的文本.设计验证码的目的是,通过验证你是真实的人来避免电脑自动填充表格.但是随着深度学习和计算机视觉的兴起,现在验证码常常易被攻破. 我拜 ...

  7. Scrum立会报告+燃尽图(十一月十七日总第二十五次):设计调查问卷;修复上一阶段bug

    此作业要求参见:https://edu.cnblogs.com/campus/nenu/2018fall/homework/2284 项目地址:https://git.coding.net/zhang ...

  8. Alpha发布用户使用报告【欢迎来怼】

    目录 用户统计表 部分用户评论截图 用户统计图 总结 一.用户统计表 目前,博客园安卓版的用户已达到11位.为了采集到更加客观公正的用户评价,并没有将团队内部人员的评价统计进来.同时,为了更好地保护用 ...

  9. c# 简单日志记录

    FileStream fs = new FileStream(System.AppDomain.CurrentDomain.BaseDirectory + "log.txt",Fi ...

  10. UVALive - 6893 The Big Painting 字符串哈希

    题目链接: http://acm.hust.edu.cn/vjudge/problem/129730 The Big Painting Time Limit: 5000MS 题意 给你一个模板串和待匹 ...