这题的话,我能玩一年
今天做了很多递推的题,这题无疑是最复杂的
其实可以看出来,2,3,4,5为一类,不妨定义为2型,1,6为一类,定义为1型
规定num[i]为结尾是i的凹槽的数量
我们可以能轻易的推出 sum = num[1]*2+num[2]*4
现在我们开始分析这个递推式的构成
根据第n个凹槽前 能不能构成一把lock,我们将情况分为两类
A:能构成lock
1.如果当前结尾为1类,我们用‘1’分析好了(下面也是用1),n-1的结尾必然不能是‘6’,因为1和6不能直接相连,根据题意就知道了,可以推出num1[i] = lock[i-1] - num1[i-1]
2.如果当前结尾为2类,那和n-1的结尾无任何关系,则num2[i] = lock[i-1]
B:加入n后才能构成lock
很容易推出前n-1应该有两种种类,因为题目说了至少有三种种类的凹槽
1.如果当前结尾是‘1’(1类),我们要分两种讨论,有‘6’和无'6',至于原因,还是因为‘6’不能放在n-1结尾处
a.取‘6’
(哎,数学符号打不出来额,文字描述好了)
从剩下的4个内取1个,组合数为4,排列数为(2^(n-2)-1) 因为n-1处不能放‘6’
b.不取‘6’
从剩下的4个内取两个,组合数为为6,排列数为(2^(n-1)-2)
2.如果当前是‘2’(2类)
从剩下的5个内取两个,但是1和6不能同时取,所以-1,则组合数为9,排列数为(2^(n-1)-2)
#include <iostream> #include <cstdio> #include <cmath> #include <algorithm> using namespace std; int main() { __int64 lock[26],num1[26],num2[26]; __int64 t; num1[3] = 16; num2[3] = 18; lock[3] = 104; t = num1[3]; for(int i=4;i<26;i++){ num1[i] = lock[i-1] - t; //sub num6[i-1] num2[i] = lock[i-1]; num1[i] += 4*((int)pow((float)2,i-2)-1)+6*((int)pow((float)2,i-1)-2); num2[i] += 9*((int)pow((float)2,i-1)-2); lock[i] = 2*num1[i] + 4*num2[i]; t = num1[i]; } for(int i=3;i<26;i++){ printf("N=%d: %I64d\n",i,lock[i]); } //cout << "Hello world!" << endl; return 0; }