OpenJ_Bailian 4103 踩方格(搜索 動態規劃 )
阿新 • • 發佈:2018-07-26
include 轉移 div spa pen ref 向上 opened .cn
題目傳送門OpenJ_Bailian 4103
描述
有一個方格矩陣,矩陣邊界在無窮遠處。我們做如下假設:
a. 每走一步時,只能從當前方格移動一格,走到某個相鄰的方格上;
b. 走過的格子立即塌陷無法再走第二次;
c. 只能向北、東、西三個方向走;
請問:如果允許在方格矩陣上走n步,共有多少種不同的方案。2種走法只要有一步不一樣,即被認為是不同的方案。
輸入
允許在方格上行走的步數n(n <= 20)
輸出
計算出的方案數量
樣例輸入
2
樣例輸出
7
解題思路:
1.遞歸:從 (i,j) 出發,走n步的方案數,等於以下三項之和:
從(i+1,j)出發,走n-1步的方案數。前提:(i+1,j)還沒走過
從(i,j+1)出發,走n-1步的方案數。前提:(i,j+1)還沒走過
從(i,j-1)出發,走n-1步的方案數。前提:(i,j-1)還沒走過
逐層往下搜。
或者用狀態轉移:
要是最後一步是向左走,則前一步不能為向右走 l[i]=l[i-1]+u[i-1]
要是最後一步是向右走,則前一步不能為向左走 r[i]=r[i-1]+u[i-1]
要是最後一步是向上走,則前一步是什麽無影響 u[i]=l[i-1]+r[i-1]+u[i-1]
可得公式:f[i]=l[i]+r[i]+u[i]
=2*l[i-1]+2*r[i-1]+3*u[i-1]
=2*f[i-1]+u[i-1]
=2*f[i-1]+f[i-2]
#include<cstdio> int vis[30][30]= {0}; int ways(int x,int y,int n) { if (n==0) return 1; vis[x][y]=1; int num=0; if (!vis[x][y-1]) num+=ways(x,y-1,n-1); if (!vis[x][y+1]) num+=ways(x,y+1,n-1); if (!vis[x+1][y]) num+=ways(x+1,y,n-1); vis[x][y]=0; return num; }遞歸搜索int main() { int n; scanf("%d",&n); printf("%d\n",ways(0,22,n)); return 0; }
#include<cstdio> int l[25],r[25],u[25]; int main() { int n; scanf("%d",&n); l[1]=r[1]=u[1]=1; for (int i=2; i<=n; i++) { l[i]=l[i-1]+u[i-1]; r[i]=r[i-1]+u[i-1]; u[i]=l[i-1]+r[i-1]+u[i-1]; } printf("%d\n",l[n]+u[n]+r[n]); return 0; }DP
#include<stdio.h> int f[22]; int main() { int n; scanf("%d",&n); f[1]=3,f[2]=7; for (int i=3; i<=n; i++) f[i]=2*f[i-1]+f[i-2]; printf("%d\n",f[n]); return 0; }公式
OpenJ_Bailian 4103 踩方格(搜索 動態規劃 )