题目链接:点我
题目
经发明了脑洞治疗仪&超能粒子炮的发明家SHTSC又公开了他的新发明:超能粒子炮·改–一种可以发射威力更加强大的粒子流的神秘装置。超能粒子炮·改相比超能粒子炮,在威力上有了本质的提升。它有三个参数n,k。它会向编号为0到k的位置发射威力为C(n,k) mod 2333的粒子流。现在SHTSC给出了他的超能粒子炮·改的参数,让你求其发射的粒子流的威力之和模2333。
Input
第一行一个整数t。表示数据组数。
之后t行,每行二个整数n,k。含义如题面描述。
k<=n<=1018,t<=10 5
Output
t行每行一个整数,表示其粒子流的威力之和模2333的值。
Sample Input
1
5 5
Sample Output
32
题意:
求C(n, i) 的和.
思路:
就是一个lucas定理和不断化简推公式的过程,鶸就不写了,
推荐一个写得还不错得博客:
http://blog.csdn.net/qzh_1430586275/article/details/51893154
代码:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 #include <cstdio> #include <algorithm> #include <cstring> #include <cmath> #include <iostream> using namespace std;typedef long long LL;const int maxn = 2333 ;LL c[maxn+2 ][maxn+2 ]; LL sum[maxn+2 ][maxn+2 ]; void init () { for (int i = 0 ; i<maxn;++i) c[i][0 ] = 1 ,sum[i][0 ] = 1 ,sum[0 ][i] = 1 ; for (int i = 1 ;i<maxn;++i) for (int j = 1 ;j<=i;++j) c[i][j]=(c[i-1 ][j-1 ]+c[i-1 ][j]) %maxn; for (int i = 1 ;i<maxn;++i) for (int j = 1 ;j<maxn;++j) sum[i][j] =sum[i][j-1 ] +c[i][j]; } LL lucas (LL n,LL k) { if (k<0 ||n<0 ) return 0 ; if (n<maxn&&k<maxn) return c[n][k]; return lucas (n/maxn,k/maxn)*c[n%maxn][k%maxn]%maxn; } LL cal (LL n,LL k) { if (k<0 ) return 0 ; return (cal (n/maxn,k/maxn-1 ) *sum[n%maxn][maxn-1 ] + lucas (n/maxn,k/maxn)*sum[n%maxn][k%maxn] )%maxn; } int main () { int t; init (); scanf ("%d" , &t); while (t--){ LL n, k; scanf ("%lld %lld" , &n, &k); printf ("%lld\n" ,cal (n,k)); } return 0 ; }