CF1329B Dreamoon Likes Sequences(组合数学)

starletkiss 2020-04-17

这道题的关键是有两个限制,1个是递增,1个是异或

那么如果我们要求递增,则i和i-1的最高位不能相同,因为这样bi就被异或导致失去最高位

因此我们知道最高位相同的数是冲突的,所以我们求取最高位为i的个数是多少个

我们发现答案是 2i----2^(i+1)-1这个区间内的数都可以,那么取值就是取值就是相减+1,另外,我们也可以不选最高位为i的数。

之后就是组合了,再每组中选一个,或者不选。但是最后要注意的是,全部都不选是不行的。

#include<iostream>
#include<algorithm>
#include<cstring>
#include<cstdio>
#include<map>
#include<string>
#include<vector>
using namespace std;
typedef long long ll;
ll mod(ll a,ll b){
    return (a%b+b)%b;
}
int main(){
    int t;
    cin>>t;
    while(t--){
        ll n,m;
        cin>>n>>m;
        ll ans=1;
        ll s=1;
        int i;
        for(i=0;i<=30;i++){
            if((1<<i)>n)
                break;
            ans=(ans*(min(n,(1ll<<i+1)-1)-(1<<i)+2))%m;
        }
        ans--;
        cout<<mod(ans,m)<<endl;
    }
    return 0;
}

相关推荐