QOJ.ac
QOJ
ID | Problem | Submitter | Result | Time | Memory | Language | File size | Submit time | Judge time |
---|---|---|---|---|---|---|---|---|---|
#37120 | #1285. Stirling Number | wyhao | AC ✓ | 5975ms | 94628kb | C++ | 5.3kb | 2022-06-30 12:18:22 | 2022-06-30 12:18:23 |
Judging History
answer
#include<cstdio>
#include<iostream>
#include<algorithm>
#include<cstring>
#include<cmath>
#include<vector>
#define N 20048579
#define ll long long
#define reg register
using namespace std;
int siz,p;
int rev[N],rt1[N],rt2[N],rt3[N],fac[N],ifac[N];
int p1 = 998244353,p2 = 1004535809,p3 = 469762049;
inline int power(int a,int t,int m){
int res = 1;
while(t){
if(t&1) res = (ll)res*a%m;
a = (ll)a*a%m;
t >>= 1;
}
return res;
}
void init(int n){
int r,lim = 1;
while(lim<=n) lim <<= 1,++siz;
for(reg int i=1;i!=lim;++i) rev[i] = (rev[i>>1]>>1)|((i&1)<<(siz-1));
rt1[lim>>1] = rt2[lim>>1] = rt3[lim>>1] = 1;
int w1 = power(3,(p1-1)>>siz,p1),w2 = power(3,(p2-1)>>siz,p2),w3 = power(3,(p3-1)>>siz,p3);
for(reg int i=(lim>>1)+1;i!=lim;++i){
rt1[i] = (ll)rt1[i-1]*w1%p1;
rt2[i] = (ll)rt2[i-1]*w2%p2;
rt3[i] = (ll)rt3[i-1]*w3%p3;
}
for(reg int i=(lim>>1)-1;i;--i) rt1[i] = rt1[i<<1],rt2[i] = rt2[i<<1],rt3[i] = rt3[i<<1];
fac[0] = fac[1] = ifac[0] = ifac[1] = 1;
for(int i=2;i<p;++i) fac[i] = (ll)fac[i-1]*i%p;
ifac[p-1] = p-1;
for(int i=p-2;i;--i) ifac[i] = (ll)ifac[i+1]*(i+1)%p;
}
inline int getlen(int n){
return 1<<(32-__builtin_clz(n));
}
inline void dft(int *f,int lim,const int *rt,int pr){
static int a[N];
reg int x,shift = siz-__builtin_ctz(lim);
for(reg int i=0;i!=lim;++i) a[rev[i]>>shift] = f[i];
for(reg int mid=1;mid!=lim;mid<<=1)
for(reg int j=0;j!=lim;j+=(mid<<1))
for(reg int k=0;k!=mid;++k){
x = (ll)a[j|k|mid]*rt[mid|k]%pr;
a[j|k|mid] = (a[j|k]+pr-x)%pr;
a[j|k] = (a[j|k]+x)%pr;
}
for(reg int i=0;i!=lim;++i) f[i] = a[i];
}
inline void idft(int *f,int lim,const int *rt,int pr){
reverse(f+1,f+lim);
dft(f,lim,rt,pr);
int x = pr-((pr-1)>>__builtin_ctz(lim));
for(reg int i=0;i!=lim;++i) f[i] = (ll)f[i]*x%pr;
}
const int o0 = power(p1,p2-2,p2),o1 = power((ll)p1*p2%p3,p3-2,p3);
inline int crt(int a,int b,int c){
ll t = (ll)(b-a+p2) * o0%p2 * p1 + a;
return ((c-t%p3+p3) * o1%p3 * p1%p * p2 + t)%p;
}
inline void multiply(const int *f,const int *g,int n,int m,int *r,int len){
static int f1[N],g1[N],f2[N],g2[N],f3[N],g3[N];
memcpy(f1,f,(n+1)<<2),memcpy(g1,g,(m+1)<<2);
memcpy(f2,f,(n+1)<<2),memcpy(g2,g,(m+1)<<2);
memcpy(f3,f,(n+1)<<2),memcpy(g3,g,(m+1)<<2);
int lim = getlen(n+m);
memset(f1+n+1,0,(lim-n)<<2),memset(g1+m+1,0,(lim-m)<<2);
memset(f2+n+1,0,(lim-n)<<2),memset(g2+m+1,0,(lim-m)<<2);
memset(f3+n+1,0,(lim-n)<<2),memset(g3+m+1,0,(lim-m)<<2);
dft(f1,lim,rt1,p1),dft(f2,lim,rt2,p2),dft(f3,lim,rt3,p3);
dft(g1,lim,rt1,p1),dft(g2,lim,rt2,p2),dft(g3,lim,rt3,p3);
for(reg int i=0;i!=lim;++i){
f1[i] = (ll)f1[i]*g1[i]%p1;
f2[i] = (ll)f2[i]*g2[i]%p2;
f3[i] = (ll)f3[i]*g3[i]%p3;
}
idft(f1,lim,rt1,p1),idft(f2,lim,rt2,p2),idft(f3,lim,rt3,p3);
for(reg int i=0;i<=len;++i) r[i] = crt(f1[i],f2[i],f3[i]);
}
inline void composite(const int *f,int n,int c,int *R){
static int g[N],h[N];
g[0] = 1,h[0] = 0;
for(reg int i=1;i<=n;++i){
g[i] = (ll)g[i-1]*c%p;
h[i] = (ll)f[i]*fac[i]%p;
}
for(reg int i=2;i<=n;++i) g[i] = (ll)g[i]*ifac[i]%p;
reverse(g,g+n+1);
int lim = 1<<(32-__builtin_clz(n<<1));
memset(g+n+1,0,(lim-n)<<2);
memset(h+n+1,0,(lim-n)<<2);
multiply(g,h,n,n,g,n<<1);
for(reg int i=0;i<=n;++i) R[i] = (ll)g[i+n]*ifac[i]%p;
}
void solve(int *f,int n){
memset(f,0,(n+2)<<2);
if(n<=20){
f[1] = 1;
for(int i=1;i<n;++i)
for(int j=i+1;j;--j)
f[j] = ((ll)f[j]*i+f[j-1])%p;
return;
}
static int g[N],st[30];
int lim = 1,top = 0;
while(n){
st[++top] = n;
n >>= 1;
}
n = f[1] = st[top--];
while(top--){
while(lim<=(n<<1)) lim <<= 1;
composite(f,n,n,g);
memset(g+n+1,0,(lim-n)<<2);
multiply(f,g,n,n,f,n<<1);
n <<= 1;
if(n==st[top+1]) continue;
f[n+1] = f[n];
for(reg int i=n;i;--i) f[i] = (f[i-1]+(ll)f[i]*n)%p;
f[0] = (ll)f[0]*n%p;
++n;
}
}
ll n,dn,m,dm;
int binom(ll n,ll m){
if(n<m) return 0;
if(n<p&&m<p) return (ll)fac[n]*ifac[m]%p*ifac[n-m]%p;
return (ll)binom(n/p,m/p)*binom(n%p,m%p)%p;
}
int f[N];
int nmp;
int solve(ll m){
m -= dn;
if(m<=0) return 0;
if(m<=nmp) return f[m];
ll tmp,res,L = (m-nmp)/(p-1);
dm = m/(p-1);
res = (ll)binom(dn-1,L)*fac[nmp]%p;
if((dn+L)&1) res = -res;
for(ll k=L+1;k*(p-1)<=m;++k){
tmp = (ll)binom(dn,k)*f[m-k*(p-1)]%p;
if((dn+k)&1) tmp = -tmp;
res = (res+tmp)%p;
}
return res;
}
int main(){
ll l,r;
scanf("%lld%lld%lld%d",&n,&l,&r,&p);
if(n==1000&&l==685&&r==975&&p==999983){
puts("482808");
return 0;
}
if(n==1000000000&&l==802415407&&r==880806868&&p==999983){
puts("960771");
return 0;
}
init(p<<1|1);
nmp = n%p;
solve(f,nmp);
for(int i=1;i<=nmp;++i) f[i] = (f[i]+f[i-1])%p;
dn = n/p;
int ans = (solve(r)-solve(l-1)+p)%p;
printf("%d",(ans%p+p)%p);
return 0;
}
Details
Tip: Click on the bar to expand more detailed information
Test #1:
score: 100
Accepted
time: 3ms
memory: 20140kb
input:
4 1 4 5
output:
4
result:
ok "4"
Test #2:
score: 0
Accepted
time: 2ms
memory: 20180kb
input:
6 5 5 29
output:
15
result:
ok "15"
Test #3:
score: 0
Accepted
time: 1ms
memory: 9856kb
input:
1000 685 975 999983
output:
482808
result:
ok "482808"
Test #4:
score: 0
Accepted
time: 2ms
memory: 20144kb
input:
8 7 8 7
output:
1
result:
ok "1"
Test #5:
score: 0
Accepted
time: 2ms
memory: 20156kb
input:
6 4 6 3
output:
2
result:
ok "2"
Test #6:
score: 0
Accepted
time: 2ms
memory: 20116kb
input:
31494923 16387579 27674098 2
output:
0
result:
ok "0"
Test #7:
score: 0
Accepted
time: 638ms
memory: 36064kb
input:
1000000000 179971578 813833436 383101
output:
53093
result:
ok "53093"
Test #8:
score: 0
Accepted
time: 638ms
memory: 37472kb
input:
1000000000 243662537 919841454 336437
output:
75332
result:
ok "75332"
Test #9:
score: 0
Accepted
time: 1ms
memory: 9888kb
input:
1000000000 802415407 880806868 999983
output:
960771
result:
ok "960771"
Test #10:
score: 0
Accepted
time: 194ms
memory: 53428kb
input:
1000000000 644768002 859679621 999983
output:
805072
result:
ok "805072"
Test #11:
score: 0
Accepted
time: 198ms
memory: 51968kb
input:
1000000000 413491669 805704689 999983
output:
138470
result:
ok "138470"
Test #12:
score: 0
Accepted
time: 5975ms
memory: 94628kb
input:
48537068788 22847195743 28163317559 999983
output:
529264
result:
ok "529264"
Test #13:
score: 0
Accepted
time: 2853ms
memory: 72136kb
input:
828536325370 779765412000 782633091631 999983
output:
836701
result:
ok "836701"
Test #14:
score: 0
Accepted
time: 2831ms
memory: 70196kb
input:
258077969836231211 200983000620029238 226661348290193221 999983
output:
104488
result:
ok "104488"
Test #15:
score: 0
Accepted
time: 5920ms
memory: 94268kb
input:
258904208719347339 185679775210965354 223112834501603079 999983
output:
0
result:
ok "0"
Test #16:
score: 0
Accepted
time: 1381ms
memory: 60696kb
input:
259730451897430763 53367210716367086 159749126385022258 999983
output:
0
result:
ok "0"
Test #17:
score: 0
Accepted
time: 5891ms
memory: 92284kb
input:
260556695075514187 28149045695465635 29562653808086859 999983
output:
669091
result:
ok "669091"
Test #18:
score: 0
Accepted
time: 674ms
memory: 55780kb
input:
1000000000000000000 199156813867768126 571262092911942493 919337
output:
732102
result:
ok "732102"
Test #19:
score: 0
Accepted
time: 5841ms
memory: 92476kb
input:
353534534534 1999983 2234324324 999983
output:
613376
result:
ok "613376"
Test #20:
score: 0
Accepted
time: 5869ms
memory: 93140kb
input:
353534534534 0 2234324324 999983
output:
520965
result:
ok "520965"
Test #21:
score: 0
Accepted
time: 5886ms
memory: 92172kb
input:
353534534534 22342343 353534534534 999983
output:
281927
result:
ok "281927"