BZOJ 3329 Xorequ

Description

Input

第一行一个正整数,表示数据组数据 ,接下来T行
每行一个正整数N

Output

2*T行
第2*i-1行表示第i个数据中问题一的解,

第2*i行表示第i个数据中问题二的解,

Sample Input

1
1

Sample Output

1
2

HINT

x=1与x=2都是原方程的根,注意第一个问题的解
不要mod 10^9+7
1<=N<=10^18
1<=T<=1000

条件转化为二进制相邻两位不能同为1

第一问大小有限制,用数位dp

第二问直接矩阵快速幂

 1 #include<iostream>
 2 #include<cstdio>
 3 #include<cstring>
 4 #include<algorithm>
 5 #include<cmath>
 6 using namespace std;
 7 typedef long long lol;
 8 struct Matrix
 9 {
10   lol a[2][2];
11 }Mat,ans;
12 int Mod=1e9+7;
13 Matrix operator *(const Matrix &a,const Matrix &b)
14 {int i,j,k;
15   Matrix res;
16   memset(res.a,0,sizeof(res.a));
17   for (i=0;i<=1;i++)
18     {
19       for (j=0;j<=1;j++)
20     {
21       for (k=0;k<=1;k++)
22         {
23           res.a[i][j]+=a.a[i][k]*b.a[k][j]%Mod;
24           res.a[i][j]%=Mod;
25         }
26     }
27     }
28   return res;
29 }
30 lol f[61][2][2],lim;
31 lol n,s,a[61],len;
32 lol dfs(int pos,int pre,int flag,int k)
33 {int i;
34   if (pos<0) return 1;
35   if (k&&f[pos][pre][flag]!=-1) return f[pos][pre][flag];
36   int ed=1;
37   lol cnt=0;
38   if (flag) ed=(n>>pos)&1;
39   for (i=0;i<=ed;i++)
40     {
41       if (pre==1&&i==1) continue;
42       cnt+=dfs(pos-1,i,flag&&(i==ed),k||(i!=0));
43     }
44   if (k) f[pos][pre][flag]=cnt;
45   return cnt;
46 }
47 void qpow(lol k)
48 {
49   Matrix res;
50   res.a[0][0]=1;res.a[0][1]=0;
51   res.a[1][1]=1;res.a[1][0]=0;
52   while (k)
53     {
54       if (k&1) res=res*Mat;
55       Mat=Mat*Mat;
56       k>>=1;
57     }
58   ans=ans*res;
59 }
60 int main()
61 {lol i,T;
62   cin>>T;
63   while (T--)
64     {
65       scanf("%lld",&n);
66       memset(f,-1,sizeof(f));
67       s=n;len=0;
68       memset(a,0,sizeof(a));
69       for (;s;s/=2)
70     a[++len]=s&1;
71       printf("%lld\n",dfs(len,0,1,0)-1);
72       memset(ans.a,0,sizeof(ans.a));
73       Mat.a[0][0]=1;Mat.a[0][1]=1;
74       Mat.a[1][0]=1;Mat.a[1][1]=0;
75       ans.a[0][0]=1;ans.a[0][1]=1;
76       qpow(n-1);
77       if (n==1) printf("2\n");
78       else 
79     printf("%lld\n",(ans.a[0][0]+ans.a[0][1])%Mod);
80     }
81 }

 

posted @ 2018-03-04 09:58  Z-Y-Y-S  阅读(149)  评论(0编辑  收藏  举报