积木画(蓝桥杯B组c++)简单易懂

题目描述

小明最近迷上了积木画,有这么两种类型的积木,分别为 I 型(大小为 2 个单位面积)和 L 型(大小为 3 个单位面积):

同时,小明有一块面积大小为 2 × N 的画布,画布由 2 × N 个 1 × 1 区域构成。小明需要用以上两种积木将画布拼满,他想知道总共有多少种不同的方式? 积木可以任意旋转,且画布的方向固定。

输入格式

输入一个整数 N,表示画布大小。

输出格式

输出一个整数表示答案。由于答案可能很大,所以输出其对 1000000007 取模后的值。

样例输入

复制

3

样例输出

复制

5

提示

五种情况如下图所示,颜色只是为了标识不同的积木:

对于所有测试用例,1 ≤ N ≤ 10000000.

解题思路:       a[i][0]:i列积木的堆法,a[i][1]:i列多一块小方格的堆法。

如:

 


或者



不管这三块是怎么放的,都叫a[3][0].
如果在此基础上右边多一个小方格就叫a[3][1],注意小方格可以在第四列上一行也可以在第四列下一行(不好找图就不给了,自行想象)

 

所以我们可以得出递推方程:

  a[i][0]=(a[i-2][0]+a[i-2][1]+a[i-1][0])%mod;
  a[i][1]=(a[i-1][0]*2+a[i-1][1])%mod;

       

画布大小为i的排法,既a[i][0]的值:

  1. 先考虑少一块I型积木的排法,既a[i-1][0],这时加上一块I型积木就行了,
  2. 再考虑少一块L型积木的排法,既a[i-2][1],这时加上一块L型积木就行了,
  3. 考虑少两块I型积木的排法,既a[i-2][0],加上两块I型积木,注意,两块必需横着加进去,如果是竖着加,就相当于第一种类型排法了,重复了。
  4. 涉及缺更多积木时,会发现无论怎么排,排法都会和上述情况重复,也就是说,以上三种情况涵盖了a[i][0]的所有排法。

所以有:

a[i][0]=(a[i-2][0]+a[i-2][1]+a[i-1][0])%mod;

a[i][1]也是同样的思路可以考虑。

而初始状态可以分析得出:

a[1][0]=1,a[2][0]=2,a[1][1]=2,a[2][1]=4;

AC代码:

        

#include <bits/stdc++.h>
using namespace std;
typedef long long LL;
#define mod 1000000007
const int N = 10000005;
LL a[N][2];
int main() {
	int n;
	a[1][0] = 1;
	a[2][0] = 2;
	a[1][1] = 2;
	a[2][1] = 4;
	cin >> n;

	if (n == 1)
		cout << 1;
	else if (n == 2)
		cout << 2;
	else {
		for (int i = 3; i <= n; i++) {
			a[i][0] = (a[i - 2][0] + a[i - 2][1] + a[i - 1][0]) % mod;
			a[i][1] = (a[i - 1][0] * 2 + a[i - 1][1]) % mod;
		}

		cout << a[n][0];
	}

	return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值