hdu 4291 (循环节+矩阵快速幂,2012成都网络选拔赛1004)

点击打开链接


最近刚学矩阵快速幂,下午做网选,马上就遇到了,竟然可以根据循环节找循环节!!!!还是做这类题目少啊!!


由1000000007求出222222224

由222222224求出183120


#include"stdio.h"
#include"string.h"
#define N 150001
#define m1 1000000007
#define m2 222222224
#define m3 183120
typedef __int64 LL;
struct node
{
	LL a[3][3];
}A;
//找循环节
void fun()
{
	LL i,t,m;
	LL g0,g1;
	g0=0;
	g1=1;
	m=m1;
/*
	由m1求m2
	由m2求m3
*/
	for(i=2;;i++)
	{
		t=(3*g1%m+g0%m)%m;
		g0=g1;
		g1=t;
		if(g0==0&&g1==1)
		{
			printf("%d\n",i-1);
			break;
		}
	}
}

//A*B%m
node mult(node A,node B,LL m)
{
	int i,j,k;
	node C;
	memset(C.a,0,sizeof(C.a));
	for(i=1;i<=2;i++)
	{
		for(j=1;j<=2;j++)
		{
			for(k=1;k<=2;k++)
			{
				C.a[i][j]+=A.a[i][k]*B.a[k][j];
				C.a[i][j]%=m;
			}
		}
	}
	return C;
}

//A^k%m
LL pow(node A,LL k,LL m)
{
	node B;
	B.a[1][1]=B.a[2][2]=1;
	B.a[1][2]=B.a[2][1]=0;	
	while(k)
	{
		if(k%2)
			B=mult(A,B,m);
		A=mult(A,A,m);
		k/=2;
	}
	return B.a[1][2]%m;
}
int main()
{
	//fun();
	LL n;
	while(scanf("%I64d",&n)!=-1)
	{
		if(n<2)printf("%d\n",n);
		else
		{
			A.a[1][1]=3;
			A.a[1][2]=A.a[2][1]=1;
			A.a[2][2]=0;
			LL ans;
			ans=pow(A,pow(A,pow(A,n,m3),m2),m1);
			printf("%I64d\n",ans);
		}
	}
	return 0;
}


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值