zoukankan      html  css  js  c++  java
  • HDU 2845 Beans

    Beans

    Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 1819    Accepted Submission(s): 921

    Problem Description
    Bean-eating is an interesting game, everyone owns an M*N matrix, which is filled with different qualities beans. Meantime, there is only one bean in any 1*1 grid. Now you want to eat the beans and collect the qualities, but everyone must obey by the following rules: if you eat the bean at the coordinate(x, y), you can’t eat the beans anyway at the coordinates listed (if exiting): (x, y-1), (x, y+1), and the both rows whose abscissas are x-1 and x+1.
    Now, how much qualities can you eat and then get ?
     
    Input
    There are a few cases. In each case, there are two integer M (row number) and N (column number). The next M lines each contain N integers, representing the qualities of the beans. We can make sure that the quality of bean isn't beyond 1000, and 1<=M*N<=200000.
     
    Output
    For each case, you just output the MAX qualities you can eat and then get.
     
    Sample Input
    4 6
    11 0 7 5 13 9
    78 4 81 6 22 4
    1 40 9 34 16 10
    11 22 0 33 39 6
     
    Sample Output
    242
     
    Source
     
    Recommend
    gaojie
     
     

    把二维按行列分解然后dp

     

    dp[i][0] 表示不取第i个能到的最大值

     

    所以dp[i][0] = Max(dp[i-1][0],dp[i-1][1]);

     

    dp[i][1] 表示取第i个能到的最大值

     

    所以dp[i][1] = dp[i-1][0]+value[i];

     

    row[i]记录下每一行的最优情况,然后再按照上面的方法进行dp

     

    #include<iostream>
    #include<cstdio>
    #include<cstring>
    
    using namespace std;
    
    const int N=200010;
    
    int m,n;
    int dp[N][2],val[N],row[N];
    
    int main(){
    
        //freopen("input.txt","r",stdin);
    
        while(~scanf("%d%d",&m,&n)){
            memset(dp,0,sizeof(dp));
            for(int i=1;i<=m;i++){
                for(int j=1;j<=n;j++){
                    scanf("%d",&val[j]);
                    dp[j][0]=max(dp[j-1][0],dp[j-1][1]);
                    dp[j][1]=dp[j-1][0]+val[j];
                }
                row[i]=max(dp[n][0],dp[n][1]);
            }
            for(int i=1;i<=m;i++){
                dp[i][0]=max(dp[i-1][0],dp[i-1][1]);
                dp[i][1]=dp[i-1][0]+row[i];
            }
            printf("%d\n",max(dp[m][0],dp[m][1]));
        }
        return 0;
    }
     
     
    挺有意思的题。 吃了一个豆豆后,上下2行的豆豆都不能吃。这个很关键,突破口就在这。那我们只要考虑一行最多能吃多少,然后得到每行最多能吃多少。这样得到的m个数排成一行,就很之前求一行的一样了,就是如果前面一个吃了,后面的就不能再吃,也就是不能相邻。这道题和树形DP那道 不能和有直接关系的上级一起出席聚会的题很像。 所以对于一行还说,状态表示dp[i][j],j要么取0,要么取1,表示第i个数取了没。
    状态转移就是dp[i][0]=max(dp[i-1][0],dp[i-1][1])   dp[i][1]=dp[i-1][0]+val[i]
    这道题只给出了M*N,不可能用2个数定一个位置。所以就用了dp[i][j],1<=i<=M*N j=0,1
    得到每行的最大值后(max(dp[i][0],dp[i][1]),i=n*k),再对这些最大值dp,方法一样,状态的第一个参数也是MAX,因为N可能为1.
     
     
    #include<stdio.h>
    #include<string.h>
    
    const int maxn=200010;
    
    int dp_row[maxn][2];
    int dp_col[maxn][2];
    
    int max(int a,int b){
        return a>b?a:b;
    }
    
    int main(){
    
        //freopen("input.txt","r",stdin);
    
        int m,n;
        while(scanf("%d%d",&m,&n)!=EOF){
            memset(dp_row,0,sizeof(dp_row));
            memset(dp_col,0,sizeof(dp_col));
            int tmp;
            for(int i=1;i<=m*n;i++){
                scanf("%d",&tmp);
                if(i%n==1){
                    dp_row[i][0]=0;
                    dp_row[i][1]=tmp;
                }else{
                    dp_row[i][0]=max(dp_row[i-1][0],dp_row[i-1][1]);
                    dp_row[i][1]=dp_row[i-1][0]+tmp;
                }
            }
            for(int i=1;i<=m;i++){
                dp_col[i][0]=max(dp_col[i-1][0],dp_col[i-1][1]);
                dp_col[i][1]=dp_col[i-1][0]+max(dp_row[i*n][0],dp_row[i*n][1]);
            }
            printf("%d\n",max(dp_col[m][0],dp_col[m][1]));
        }
        return 0;
    }
  • 相关阅读:
    Python 模块 itertools
    Python 字符串的encode与decode
    python 模块 hashlib(提供多个不同的加密算法)
    暴力尝试安卓gesture.key
    hdu 1300 Pearls(DP)
    hdu 1232 畅通工程(并查集)
    hdu 1856 More is better(并查集)
    hdu 1198 Farm Irrigation(并查集)
    hdu 3635 Dragon Balls(并查集)
    hdu 3038 How Many Answers Are Wrong(并查集)
  • 原文地址:https://www.cnblogs.com/jackge/p/2979861.html
Copyright © 2011-2022 走看看