链接:登录—专业IT笔试面试备考平台_牛客网
来源:牛客网
题目大意:
求有多少长为 n 的元素是 [0, 2 m) 的整数序列
满足存在一个非空子序列的 AND 和是 1
答案对输入的正整数 q 取模
1 ≤ n, m ≤ 5000, 1 ≤ q ≤ 1e9
思路:
由于需要子序列按位与的结果为1,所以必须要由奇数按位与得到,且二进制除最低为外其余位必须包含一个0;因此这种情况可以由k个奇数按位与得到其余位置上可以填任意的值;于是我们可以推出k个数在每一位二进制位上的情况得到但由于有全1的情况所以要减1;便可得出有效子序列的组成部分;对于剩下携带的任意数的每一二进制位上的情况为
;最后乘上组合数(用杨辉三角打表求出)用以求不同的奇数组合得到最终公式:
ac代码:
#include<bits/stdc++.h>
using namespace std;
#define int long long
int n,m,q;
int c[5005][5005];
int ksm(int a,int b){
int ans=1;
while(b){
if(b&1) ans=ans*a%q;
a=a*a%q;
b>>=1;
}
return ans;
}
signed main(){
cin>>n>>m>>q;
for(int i=0;i<=5000;i++){
c[i][0]=1;
for(int j=1;j<=i;j++) c[i][j]=(c[i-1][j]+c[i-1][j-1])%q;
}
int sum=0;
for(int k=1;k<=n;k++){
int s=ksm(2,m-1);
int t=ksm(ksm(2,k)-1+q,m-1);
sum=(sum+1ll*ksm(s,(n-k))*t%q*c[n][k])%q;
}
cout<<sum<<endl;
return 0;
}