PAT 1045 Favorite Color Stripe

使用DP,递推关系见代码,先使用大空间的dp数组

#include <cstdio>
#include <cstdlib>
#include <vector>

using namespace std;

int max(int a, int b) {return a>b?a:b;}

int main() {
    int N, M, L, tmp;
    scanf("%d", &N);
    
    scanf("%d", &M);
    if (M < 1) return 0;
    vector<char> MColors(M);
    
    for (int i=0; i<M; i++) {
        scanf("%d", &tmp);
        MColors[i] = tmp;
    }
    
    scanf("%d", &L);
    if (L < 1) return 0;
    vector<char> LColors(L);
    
    for (int i=0; i<L; i++) {
        scanf("%d", &tmp);
        LColors[i] = tmp;
    }
    
    int rows = L + 1;
    int cols = M + 1;
    int total= rows * cols;
    int* dp = new int[rows * cols];
    
    for (int i=cols * (rows - 1); i<total; i++) {
        // set last row to zero;
        dp[i] = 0; 
    }
    for (int i=cols-1; i<total; i+=cols) {
        // set last column to zero;
        dp[i] = 0;
    }
    
    for (int i=rows-2; i>=0; i--) {
        int base = i * cols;
        for (int j=cols - 2; j>=0; j--) {
            int mc = MColors[j];
            int lc = LColors[i];
            if (mc == lc) {
                dp[base + j] = dp[base + j + cols] + 1;
            } else {
                dp[base + j] = max(dp[base + j + 1],
                                    dp[base + j + cols]);
            }
        }
    }
    printf("%d\n", dp[0]);
    return 0;
}

因为递推中只使用了当前行和下一行中的数据,题目又不要求给出完整解,因而可以优化空间如下:

#include <cstdio>
#include <cstdlib>
#include <vector>

using namespace std;

int max(int a, int b) {return a>b?a:b;}

int main() {
    int N, M, L, tmp;
    scanf("%d", &N);
    
    scanf("%d", &M);
    if (M < 1) return 0;
    vector<char> MColors(M);
    
    for (int i=0; i<M; i++) {
        scanf("%d", &tmp);
        MColors[i] = tmp;
    }
    
    scanf("%d", &L);
    if (L < 1) return 0;
    vector<char> LColors(L);
    
    for (int i=0; i<L; i++) {
        scanf("%d", &tmp);
        LColors[i] = tmp;
    }

    int cols = M + 1;
    vector<int> curr_row(cols, 0);
    vector<int> next_row(cols, 0);
    
    for (int i = L-1; i >=0; i--) {
        for (int j = M - 1; j>=0; j--) {
            if (MColors[j] == LColors[i]) {
                curr_row[j] = next_row[j] + 1;
            } else {
                curr_row[j] = max(next_row[j], curr_row[j + 1]);
            }
        }
        swap(curr_row, next_row);
    }
    printf("%d\n", next_row[0]);
    return 0;
}

即使用两个数组curr_row, next_row交替模拟整个dp数组

 

posted @ 2014-11-09 19:43  卖程序的小歪  阅读(263)  评论(0编辑  收藏  举报