该题开始未想到正解,但是一开始的问题是将m的二进制位组成不同的数,组成1个,2个...,然后用组合数即可,然后想到了第二类斯特林数的含义是将n个不同的元素放在m个相同盒子里的方案数(且不能为空集),此时我们可以将二进制个数看成n个不同元素,此时,盒子即为分成的数的个数,再套上组合学公式即可。(注意特判0)
using namespace std;
#define maxn 105
#define ll long long
#define int long long
#define mod 1000000007
ll s2[maxn][maxn];
ll kup(ll a,ll b){
ll ans = 1;
a %= mod;
while(b){
if(b & 1) ans = ans * a % mod;
a = a * a % mod;
b >>= 1;
}
return ans % mod;
}
void init()
{
s2[1][1] = 1;
for(int i = 2;i < maxn;i++){
for(int j = 1;j < maxn;j++){
s2[i][j] = (s2[i-1][j-1] + j * s2[i-1][j])%mod;
}
}
}
ll C(ll n, ll m){
ll ans = 1;
for(int i = n;i >= n - m + 1;i--){
ans = ans * (i % mod) % mod;
}
for(int i = 1;i <= m;i++){
ans = ans * kup(i, mod - 2) % mod;
}
return ans % mod;
}
ll fac(ll n){
ll ans = 1;
for(int i = n;i >= 1;i--){
ans = ans * i % mod;
}
return ans % mod;
}
signed main(){
int n,m;
scanf("%lld%lld",&n,&m);
if(m == 0){
printf("1\n");
return 0;
}
init();
ll t = m;
int cnt = 0;
while(t){
if(t % 2) cnt++;
t /= 2;
}
ll ans = 0;
for(int i = 1;i <= min(n, cnt);i++){
ans += C(n, i) % mod * fac(i) % mod * s2[cnt][i] % mod;
ans %= mod;
}
printf("%lld\n",ans % mod);
return 0;
}