Poj-3420 Quad Tiling

31 篇文章 0 订阅
30 篇文章 0 订阅

题意:

给出n和m,在一个4xn的地面上铺1x2的骨牌,求方案数;

答案对m取模,多组数据;


题解:

这个显然就是骨牌覆盖问题嘛;

状压dp搞一搞就好啦;

然后我RE+TLE之后发现,n<=109

这个就不好搞了,要用log级算法才行;

于是就用矩阵乘法,做一个16x16的矩阵,表示各种状态之间的转移;

初始矩阵就是a[0][0]=1,其他为0;

至于用来快速幂的矩阵我用TLE的程序跑了一个,手算也行吧(笑);

(反正如果我手算估计wa一天)


代码:

#include<stdio.h>
#include<string.h>
#include<algorithm>
#define L 16
using namespace std;
typedef long long ll;
ll mod,f[100][100];
struct matrix
{
	ll a[L][L];
}In,st,en,T;
matrix mul(matrix x,matrix y)
{
	matrix ret;
	ll i,j,k;
	for(i=0;i<L;i++)
		for(j=0;j<L;j++)
			for(k=0,ret.a[i][j]=0;k<L;k++)
				ret.a[i][j]=(ret.a[i][j]+(x.a[i][k]*y.a[k][j]))%mod;
	return ret;
}
matrix pow(matrix x,ll y)
{
	matrix ret=In;
	while(y)
	{
		if(y&1)
		{
			ret=mul(ret,x);
		}
		y>>=1;
		x=mul(x,x);
	}
	return ret;
}
int main()
{
    ll n,m,i,j,k;
    T.a[0][0]=1;	T.a[0][3]=1;	T.a[0][9]=1;
	T.a[0][12]=1;	T.a[1][2]=1;	T.a[1][8]=1;
	T.a[1][14]=1;	T.a[2][1]=1;	T.a[2][13]=1;
	T.a[3][0]=1;	T.a[3][12]=1;	T.a[4][8]=1;
	T.a[4][11]=1;	T.a[5][10]=1;	T.a[6][9]=1;
	T.a[7][8]=1;	T.a[8][1]=1;	T.a[8][4]=1;
	T.a[8][7]=1;	T.a[9][0]=1;	T.a[9][6]=1;
	T.a[10][5]=1;	T.a[11][4]=1;	T.a[12][0]=1;
	T.a[12][3]=1;	T.a[13][2]=1;	T.a[14][1]=1;
	T.a[15][0]=1;	T.a[0][15]=1;
	for(i=0;i<L;i++)	In.a[i][i]=1;
    while(scanf("%lld%lld",&n,&m)&&(n||m))
    {
    	mod=m;
	    st.a[0][0]=1;
	    en=mul(st,pow(T,n));
        printf("%lld\n",en.a[0][0]);
    }
}

ww140142

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值