【DP】ZOJ 2852 Deck of Cards

ZOJ 2852 Deck of Cards

參考自:AC_Von

f[j][k][l]表示slot x1, x2, x3的值爲j,k,l時的最優值。pre[j][k][l]表示他的前一個狀態。

#include <iostream>
#include <algorithm>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <cmath>
using namespace std;

int f[30][30][30], p[30][30][30];

int char2num(char c){
    if(c>='2' && c<='9') return c-'0';
    if(c == 'A') return 1;
    if(c == 'F') return -1;
    return 10;
}

int main(int argc, char const *argv[])
{
    // freopen("in", "r", stdin);
    int n;
    while(scanf("%d", &n), n){
        memset(f, 0, sizeof(f));
        memset(p, 0, sizeof(p));
        char str[2];
        int ans = 0, t, tt;
        scanf("%s", str);
        t = char2num(str[0]);
        if(t == -1){
            p[0][0][0] = 350;
            ans = 350;
        }else{
            p[t][0][0] = 50;
            p[0][t][0] = 50;
            p[0][0][t] = 50;
            ans = 0;
        }

        for(int i = 0; i < n-1; i++){
            scanf("%s", str);
            t = char2num(str[0]);

            for(int j=0; j<22; j++){
                for(int k=0; k<22; k++){
                    for(int l=0; l<22; l++){
                        if((tt = p[j][k][l]) == 0) continue;

                        //1x
                        if((t == -1 && j < 21) || t + j == 21) {
                            f[0][k][l] = max(f[0][k][l], tt + 150);
                        } else if(t + j < 21) {
                            f[j+t][k][l] = max(f[t+j][k][l], tt + 50);
                        } else if(t + j > 21 && j < 21) {
                            f[21][k][l] = max(f[21][k][l], tt + 50);
                        }

                        //2x
                        if((t == -1 && k < 21) || t + k == 21) {
                            f[j][0][l] = max(f[j][0][l], tt + 250);
                        } else if(t + k < 21) {
                            f[j][t+k][l] = max(f[j][t+k][l], tt + 50);
                        } else if(t + k > 21 && k < 21) {
                            f[j][21][l] = max(f[j][21][l], tt + 50);
                        }

                        //3x
                        if((t == -1 && l < 21) || t + l == 21) {
                            f[j][k][0] = max(f[j][k][0], tt + 350);
                        } else if(t + l < 21) {
                            f[j][k][l+t] = max(f[j][k][l+t], tt + 50);
                        } else if(t + l > 21 && l < 21) {
                            f[j][k][21] = max(f[j][k][21], tt + 50);
                        }


                    }
                }
            }

            for(int j=0; j<22; j++){
                for(int k=0; k<22; k++){
                    for(int l=0; l<22; l++){
                        p[j][k][l] = f[j][k][l];
                        ans = max(ans, p[j][k][l]);
                        f[j][k][l] = 0;
                    }
                }
            }
        }

        printf("%d\n", ans);

    }
    return 0;
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章