HDU 1995 汉诺塔V
题目:http://acm.hdu.edu.cn/showproblem.php?pid=1995
题意:经典汉诺塔题型,输出第k个盘子移动的次数。
解法:
首先:由于比k小的盘子移动不会牵扯k移动,所以问题被简化成n-k+1阶汉诺塔中第一个盘子的移动次数。
再观察汉诺塔的移动策略:
1)将A上n-1个盘子借助C座先移到B座上;
2)把A座上剩下的一个盘移到C座上;
3)将n-1个盘从B座借助于A座移到C座上。
步骤2)中该盘子未移动,所以递推公式f[n]=2*f[n-1],
由于问题已经转化成n-k+1阶汉诺塔,故所求通项f[n]=2^(n-k).
dp[i][j] :记录挪i个盘子第j个盘子需要挪的次数;
dp[i][j] = d[i-1][j]*2 ; if i==j , dp[i][j] =1;
AC:
#include <bits/stdc++.h> using namespace std; typedef long long LL; const int imax = 62; LL dp[imax][imax]; int t,n,k; int main() { memset(dp,0,sizeof(dp)); dp[1][1] = 1; for(int i = 2 ; i < imax ; i++) { for(int j = 1 ; j < i ; j++) dp[i][j] = dp[i-1][j]<<1;//递推公式f(n) = 2*f(n-1); dp[i][i] = 1; } cin >>t; while(t--) { cin >> n >> k; cout << dp[n][k] <<endl; } return 0; }