HDU 4686

再不能直视这道题,换INT64就过了。。。。。。。

同样可以使用矩阵的方法。构造1*5的

D[N],a[n],b[n],a【n】*b[n],1

接着你应该就会了。

#include <iostream>
#include <cstdio>
#include <algorithm>
#define LL __int64

using namespace std;

const LL Mod=1000000007;

struct Matrax{
	LL m[6][6];
};
LL N,A0, AX, AY,B0, BX, BY;

Matrax a,per;

void initial(){
	for(int i=0;i<5;i++){
		for(int j=0;j<5;j++)
		a.m[i][j]=per.m[i][j]=0;
	}
	for(int i=0;i<5;i++)
	per.m[i][i]=1;
	a.m[0][0]=a.m[3][0]=1;
	a.m[1][1]=(AX); a.m[4][1]=(AY);
	a.m[2][2]=(BX); a.m[4][2]=(BY);
	a.m[1][3]=(AX* BY)%Mod;
	a.m[2][3]=(AY* BX)%Mod; a.m[3][3]= (AX* BX)%Mod;
	a.m[4][3]=(AY* BY)%Mod;
	a.m[4][4]=1;
}

Matrax multi(Matrax a,Matrax b){
	Matrax c;
	for(int i=0;i<5;i++){
		for(int j=0;j<5;j++){
			c.m[i][j]=0;
			for(int k=0;k<5;k++)
			c.m[i][j]=(c.m[i][j]+a.m[i][k]*b.m[k][j])%Mod;
		}
	}
	return c;
}

Matrax quick(LL  k){
	Matrax ans=per,p=a;
	while(k){
		if(k&1){
			ans=multi(ans,p);
		}
		k>>=1;
		p=multi(p,p);
	}
	return ans;
}

LL ts[5];

int main(){
	while(scanf("%I64d%I64d%I64d%I64d%I64d%I64d%I64d",&N,&A0,&AX,&AY,&B0,&BX,&BY)!=EOF){
//	while(scanf("%lld%lld%lld%lld%lld%lld%lld",&N,&A0,&AX,&AY,&B0,&BX,&BY)!=EOF){
		LL tp=0;
		if(N==0){ printf("0\n"); continue; }
		A0%=Mod; B0%=Mod;
		AX%=Mod; AY%=Mod;
		BX%=Mod; BY%=Mod;
		ts[0]=A0*B0%Mod;
		ts[1]=(A0*AX+AY)%Mod;
		ts[2]=(B0*BX+BY)%Mod;
		ts[3]=(ts[1]*ts[2])%Mod;
		ts[4]=1;
		initial();
		Matrax ans=quick(N-1);
		for(int i=0;i<5;i++){
			tp=(tp+ts[i]*ans.m[i][0])%Mod;
		}
	//	printf("%lld\n",tp%Mod);
	printf("%I64d\n",tp%Mod);
	}
	return 0;
}

  

时间: 2024-10-12 07:59:49

HDU 4686的相关文章

HDU 4686 Arc of Dream(矩阵快速幂)

题目地址:HDU 4686 我去..因为忘记把函数里的k定义成64位的,导致TLE了一晚上...晕.. 这题没什么技巧,就是根据公式构造就行. 代码如下: #include <iostream> #include <cstdio> #include <string> #include <cstring> #include <stdlib.h> #include <math.h> #include <ctype.h> #in

HDU 4686 Arc of Dream(快速幂矩阵)

题目链接 再水一发,构造啊,初始化啊...wa很多次啊.. #include <cstring> #include <cstdio> #include <string> #include <iostream> #include <algorithm> #include <vector> #include <queue> using namespace std; #define MOD 1000000007 #define

hdu 4686 矩阵乘法优化递推关系

这里有一份解题报告 解题报告 这是理论知识: 点我 最主要的是构造乘法矩阵,这个是通过递推关系得到的. 有了它,求数列的第n项可以在log(n)的时间里求出来. 1 #include <iostream> 2 #include <cstdio> 3 #include <cstring> 4 #include <set> 5 #include <algorithm> 6 #include <map> 7 #include<vect

HDU 4686 Arc of Dream 矩阵快速幂,线性同余 难度:1

http://acm.hdu.edu.cn/showproblem.php?pid=4686 当看到n为小于64位整数的数字时,就应该有个感觉,acm范畴内这应该是道矩阵快速幂 Ai,Bi的递推式题目已经给出, Ai*Bi=Ax*Bx*(Ai-1*Bi-1)+Ax*By*Ai-1+Bx*Ay*Bi-1+Ay*By AoD(n)=AoD(n-1)+AiBi 构造向量I{AoD(i-1),Ai*Bi,Ai,Bi,1} 初始向量为I0={0,A0*B0,A0,B0,1} 构造矩阵A{ 1,0,0,0,

hdu 4686 Arc of Dream 自己推 矩阵快速幂

A.mat[0][0] = 1, A.mat[0][1] = 1, A.mat[0][2] = 0, A.mat[0][3] = 0, A.mat[0][4] = 0; A.mat[1][0] = 0, A.mat[1][1] = AX*BX%Mod, A.mat[1][2] = AX*BY%Mod, A.mat[1][3] = AY*BX%Mod, A.mat[1][4] = AY*BY%Mod; A.mat[2][0] = 0, A.mat[2][1] = 0, A.mat[2][2] =

hdu 4686 (矩阵快速幂)

题意: a 0 = A0          a i = a i-1*AX+AY          b 0 = B0          b i = b i-1*BX+BY 求AoD(N) mod 1000000007 思路: 做这道题时思路没有打开,一直纠结于如何把公式加一起..... 正确是做法是把AoD这个和加到你的构造矩阵里来递推计算 aibi=(Ax*Bx)*ai-1*bi-1 + (Ax*By)*ai-1 + (Ay*Bx)*bi-1 + Ay*By 代码: #include <cstd

hdu 4686 Arc of Dream(矩阵快速幂乘法)

Problem Description An Arc of Dream is a curve defined by following function: where a0 = A0 ai = ai-1*AX+AY b0 = B0 bi = bi-1*BX+BY What is the value of AoD(N) modulo 1,000,000,007? Input There are multiple test cases. Process to the End of File. Eac

HDU 4686 (推公式+矩阵快速幂)

题目连接:传送门 题意: 给定ai,bi的推倒公式,求sigma(ai*bi) ( 0<= i < n) 分析: A0 = A0 Ai = Ai-1*Ax+Ay B0 = B0 Bi = Bi-1*Bx+By 设Fi表示Ai*Bi Fi = Ai * Bi ===>    Fi = (Ai-1*Ax + Ay)*(Bi-1*Bx + By) ===>    Fi = Ax*Bx*(Ai-1*Bi-1) + Ax*By*Ai-1 + Bx*Ay*Bi-1 ===>    Fi

HDU 4686 Arc of Dream

矩阵快速幂 #include<cstdio> #include<cstring> #include<cmath> #include<algorithm> using namespace std; struct Matrix { long long A[10][10]; Matrix operator*(Matrix b); }; const long long MOD=1000000007; long long R,C; long long N,A0,AX,