zoukankan      html  css  js  c++  java
  • POJ 2385 Apple Catching

      比起之前一直在刷的背包题,这道题可以算是最纯粹的dp了,写下简单题解。

      题意是说cows在1树和2树下来回移动取苹果,有移动次数限制,问最后能拿到的最多苹果数,含有最优子结构性质,大致的状态转移也不难想出,以 dp[i][j] 表示第 i 分钟使用了 j 次移动机会时能获得的最多苹果数(不需3维,因为 j 隐含着在1树还是2树的信息,判奇偶性即可,一开始 0min 时在1树),大体的状态转移方程就是:

      dp[i][j] = j & 1 ? c[i][2] : c[i][1] + max ( dp[i+1][j], dp[i+1][j+1] ) ,  if ( j<w )

                       +  dp[i+1][j] ,             else

      上式中的 j&1 就是判断此时 dp[i][j] 是位于1树还是2树,把苹果下落位置用数组c[]记录下来(可以在草稿纸上直观地画出来),代码也就不难写出来了:

     1 #include<cstdio>
     2 #include<cstring>
     3 #include<algorithm>
     4 using namespace std;
     5 
     6 int dp[1003][33];
     7 bool c[1003][3];
     8 
     9 int main(){
    10     int t,w,i,j,x;
    11     while(~scanf("%d%d",&t,&w)){
    12         memset(c,0,sizeof(c));
    13         for(i=1; i<=t; ++i){
    14             scanf("%d",&x);
    15             c[i][x]= 1;
    16         }
    17         for(j=0; j<=w; ++j)
    18             dp[t][j]= j&1? c[t][2]:c[t][1];
    19         for(i= t-1; i>=1; --i){
    20             int tmp= min(i,w);
    21             for(j=0; j<=tmp; ++j){
    22                 dp[i][j]= j&1? c[i][2]:c[i][1];
    23                 if(j<w)      dp[i][j]+= max(dp[i+1][j],dp[i+1][j+1]);
    24                 else    dp[i][j]+= dp[i+1][j];
    25             }
    26         }
    27         printf("%d
    ",max(dp[1][0],dp[1][1]));
    28     }
    29     return 0;
    30 }

      我也看到有人用更精简的代码还有能把空间优化到一维的,但为了直观性,能让自己看懂,我也不想去折腾那些了,曾经的强迫症是时候要放一放了,全力刷题才是王道,看到自己那么一丁点儿的可怜的刷题量,和师兄几乎差了一个数量级的题量,对每一道题就不想大费周章地去追求尽善尽美了。

  • 相关阅读:
    《精通并发与Netty》学习笔记(07
    《精通并发与Netty》学习笔记(06
    《精通并发与Netty》学习笔记(05
    《精通并发与Netty》学习笔记(04
    《精通并发与Netty》学习笔记(03
    《精通并发与Netty》学习笔记(02
    《精通并发与Netty》学习笔记(01
    pymssql查询结果中文乱码处理
    使用装饰器完成python运行时类型检查
    pyttsx3实现文字转语音
  • 原文地址:https://www.cnblogs.com/Newdawn/p/4316499.html
Copyright © 2011-2022 走看看