1. 程式人生 > >遞迴的函式——三維陣列+動態規劃

遞迴的函式——三維陣列+動態規劃

Think:
1動態規劃—百度百科
2動態規劃——將多階段過程轉化為單階段問題,然後逐個求解

遞迴的函式
Time Limit: 1000MS Memory Limit: 65536KB

Problem Description
給定一個函式 f(a, b, c):
如果 a ≤ 0 或 b ≤ 0 或 c ≤ 0 返回值為 1;
如果 a > 20 或 b > 20 或 c > 20 返回值為 f(20, 20, 20);
如果 a < b 並且 b < c 返回 f(a, b, c−1) + f(a, b−1, c−1) − f(a, b−1, c);
其它情況返回 f(a−1, b, c) + f(a−1, b−1, c) + f(a−1, b, c−1) − f(a-1, b-1, c-1)。
看起來簡單的一個函式?你能做對嗎?

Input
輸入包含多組測試資料,對於每組測試資料:
輸入只有一行為 3 個整數a, b, c(a, b, c < 30)。

Output
對於每組測試資料,輸出函式的計算結果。

Example Input
1 1 1
2 2 2

Example Output
2
4

Hint

Author
qinchuan

以下為Time Limit Exceeded程式碼——暴力遞迴

#include <bits/stdc++.h>

using namespace std;

int Ans(int a, int b, int c);

int main()
{
    int
a, b, c; while(scanf("%d %d %d", &a, &b, &c) != EOF) { printf("%d\n", Ans(a, b, c)); } return 0; } int Ans(int a, int b, int c) { if(a <= 0 || b <= 0 || c <= 0) return 1; else if(a > 20 || b > 20 || c > 20) return Ans(20, 20, 20); else
if(a < b && b < c) return Ans(a, b, c-1) + Ans(a, b-1, c-1) - Ans(a, b-1, c); else return Ans(a-1, b, c) + Ans(a-1, b-1, c) + Ans(a-1, b, c-1) - Ans(a-1, b-1, c-1); } /*************************************************** User name: Result: Time Limit Exceeded Take time: 1010ms Take Memory: 0KB Submit time: 2017-04-15 17:07:12 ****************************************************/

以下為Accepted程式碼——三維陣列記錄子問題的求解結果,減少重複運算

#include <bits/stdc++.h>

using namespace std;

int vid[24][24][24];

int Ans(int a, int b, int c);

int main()
{
    int a, b, c;
    memset(vid, 0, sizeof(vid));
    while(scanf("%d %d %d", &a, &b, &c) != EOF)
    {
        printf("%d\n", Ans(a, b, c));
    }
    return 0;
}
int Ans(int a, int b, int c)
{
    if(a <= 0 || b <= 0 || c <= 0)
        return 1;
    else if(a > 20 || b > 20 || c > 20)
        return Ans(20, 20, 20);

    if(vid[a][b][c] != 0)
        return vid[a][b][c];

    if(a < b && b < c)
        vid[a][b][c] = Ans(a, b, c-1) + Ans(a, b-1, c-1) - Ans(a, b-1, c);
    else
        vid[a][b][c] = Ans(a-1, b, c) + Ans(a-1, b-1, c) + Ans(a-1, b, c-1) - Ans(a-1, b-1, c-1);
    return vid[a][b][c];
}


/***************************************************
User name: 
Result: Accepted
Take time: 20ms
Take Memory: 212KB
Submit time: 2017-04-15 17:11:16
****************************************************/