Binary Vector
题目描述:
设
,每天
从
即维度为n,每一位由01组成的所有向量的集合
中随机选择一个二进制向量。现在他想知道n天中选取n个线性独立向量的概率。请告诉
每个排列的答案,用
表示。其中
是
模
的乘法逆元。
设
表示
的答案,最后输出
,
表示异或。
线性独立介绍
对于问题
,
是仅包含
和
的
维向量
输入描述:
输入包含多个测试用例。 输入的第一行包含一个整数 ,表示测试用例的数量。在接下来的 行中,每行包含一个整数 ,描述一个测试用例。
输出描述:
对于每个测试用例,输出一个整数来表示答案。
样例输入:
3
1
2
3
样例输出:
500000004
194473671
861464136
说明:
f(1)=1/2
f(2)=3/8
f(3)=21/64
思路:
暴力出奇迹,打表出省一
打表。
打
的表。
首先讲一下线性独立,就是说:任意一个向量都不能通过其他向量加减得到,也就是所有的向量都不共面
考虑选取
个向量,对于
,有
个向量是不与选择的向量独立
那么在一个
维的空间内,选取
个向量共面的概率是
那么 维的空间内,选取 个向量线性独立的概率就是
所以:
这样我们就可以打表了。
AC Code:
#include<bits/stdc++.h>
using namespace std;
const int MAXN=2e7+5;
const int mod=1e9+7;
int T,n,mul[MAXN],inv[MAXN],ans[MAXN],x;
int ksm(int a,int b)
{
int r=1;
while(b)
{
if(b&1) r=1ll*r*a%mod;
a=1ll*a*a%mod;
b>>=1;
}
return r;
}
int main()
{
mul[0]=1;
for(int i=1;i<=MAXN;i++)
mul[i]=2ll*mul[i-1]%mod;
inv[MAXN]=ksm(mul[MAXN],mod-2);
for(int i=MAXN-1;i;i--)
inv[i]=2ll*inv[i+1]%mod;
ans[1]=x=inv[1];
for(int i=2;i<=MAXN;i++)
{
x=1ll*x*(mul[i]-1)%mod*inv[i]%mod;
ans[i]=ans[i-1]^x;
}
scanf("%d",&T);
while(T--)
{
scanf("%d",&n);
printf("%d\n",ans[n]);
}
}