【DP】POJ-1157 LITTLE SHOP OF FLOWERS

LITTLE SHOP OF FLOWERS

Time Limit: 1000MS Memory Limit: 10000K

Description

You want to arrange the window of your flower shop in a most pleasant way. You have F bunches of flowers, each being of a different kind, and at least as many vases ordered in a row. The vases are glued onto the shelf and are numbered consecutively 1 through V, where V is the number of vases, from left to right so that the vase 1 is the leftmost, and the vase V is the rightmost vase. The bunches are moveable and are uniquely identified by integers between 1 and F. These id-numbers have a significance: They determine the required order of appearance of the flower bunches in the row of vases so that the bunch i must be in a vase to the left of the vase containing bunch j whenever i < j. Suppose, for example, you have bunch of azaleas (id-number=1), a bunch of begonias (id-number=2) and a bunch of carnations (id-number=3). Now, all the bunches must be put into the vases keeping their id-numbers in order. The bunch of azaleas must be in a vase to the left of begonias, and the bunch of begonias must be in a vase to the left of carnations. If there are more vases than bunches of flowers then the excess will be left empty. A vase can hold only one bunch of flowers.

Each vase has a distinct characteristic (just like flowers do). Hence, putting a bunch of flowers in a vase results in a certain aesthetic value, expressed by an integer. The aesthetic values are presented in a table as shown below. Leaving a vase empty has an aesthetic value of 0.

V A S E S|1|2|3|4|5

—|—|—|—

Bunches

1 (azaleas)

7 23 -5 -24 16

2 (begonias)

5 21 -4 10 23

3 (carnations)

-21

5 -4 -20 20

According to the table, azaleas, for example, would look great in vase 2, but they would look awful in vase 4.

To achieve the most pleasant effect you have to maximize the sum of aesthetic values for the arrangement while keeping the required ordering of the flowers. If more than one arrangement has the maximal sum value, any one of them will be acceptable. You have to produce exactly one arrangement.

Input

The first line contains two numbers: F, V.
The following F lines: Each of these lines contains V integers, so that Aij is given as the jth number on the (i+1)st line of the input file. 

1 <= F <= 100 where F is the number of the bunches of flowers. The bunches are numbered 1 through F.
F <= V <= 100 where V is the number of vases.
-50 <= Aij <= 50 where Aij is the aesthetic value obtained by putting the flower bunch i into the vase j.

Output

The first line will contain the sum of aesthetic values for your arrangement.

Sample Input

3 5

7 23 -5 -24 16

5 21 -4 10 23

-21 5 -4 -20 20

Sample Output

53

Source

IOI 1999



题意: 有n多花要放在m个花盆里,其中第i+1种花必须放在第i朵花后面,特定的花放在特定的花盆里有不一样的权值,求出所能得到的最大权值。

思路: 简单DP,用dp[i][j]表示前i朵花已经放进前j个花盆里的权值和,则状态转移方程非常好想:

dp[i][j] = max{dp[i][j-1], dp[i-1][j-1]+w[i][j]}

决策: 要么花i放进花盆j里,要么花i放在前j-1个花盆里了。

注意: 状态转移方程最重要的就是状态必须是确定的,没有丝毫纰漏和瑕疵的。也就是说,当前dp值必须由已经确定、不会再改变的状态当中转移过来,否则错误。

P.S. 一开始我思考的决策是:要么放在当前花盆,要么放在后面的花盆,这是明显错误的,因为放在后面的花盆里这种状态是不确定的,所以dp值没有意义。

代码如下:

/*
 * ID: j.sure.1
 * PROG:
 * LANG: C++
 */
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <algorithm>
#include <ctime>
#include <cmath>
#include <stack>
#include <queue>
#include <vector>
#include <map>
#include <set>
#include <string>
#include <iostream>
#define PB push_back
#define LL long long
using namespace std;
const int INF = 0x3f3f3f3f;
const double eps = 1e-8;
/****************************************/
const int N = 105;
int n, m;
int w[N][N], dp[N][N];

int solve()
{
    for(int i = 1; i <= n; i++) {
        dp[i][i] = dp[i-1][i-1] + w[i][i];//初始化,花i最初至少在花盆i中,不能再靠前
        for(int j = i+1; j <= m; j++) {//dp[i][i]不可以被复写
            dp[i][j] = max(dp[i-1][j-1] + w[i][j], dp[i][j-1]);
        }//状态必须是已经确定的,所以决策是:要么放在这儿了,要么之前已经放过了
    }
    return dp[n][m];
}

int main()
{
#ifdef J_Sure
    freopen("000.in", "r", stdin);
    //freopen("999.out", "w", stdout);
#endif
    scanf("%d%d", &n, &m);
    for(int i = 1; i <= n; i++) {
        for(int j = 1; j <= m; j++) {
            scanf("%d", &w[i][j]);
        }
    }
    int ans = solve();
    printf("%d\n", ans);
    return 0;
}
时间: 2024-10-11 22:28:03

【DP】POJ-1157 LITTLE SHOP OF FLOWERS的相关文章

POJ 1157 LITTLE SHOP OF FLOWERS (线性dp)

OJ题目:click here~~ 题目分析:f个束花,编号为1-- f.v个花瓶,编号为1 -- v.编号小的花束,所选花瓶的编号也必须比编号大的花束所选花瓶的编号小,即花i 选k, 花j选t ,如果i < j ,则定有k < t . 如果 i > j , 则定有 k > t . 每束花放在每个花瓶里有一个值.求f束花,能得到的最大值. 设dp[ i ][ j ] 为第 i 束花选择了第 j 个花瓶 , 则转移方程为 dp[ i ][ j ] =  max(dp[ i  - 1]

poj - 1157 - LITTLE SHOP OF FLOWERS(dp)

题意:F朵花(从左到右标号为1到F,1 <= F <= 100)放入V个花瓶(从左到右标号为1到V,F <= V <= 100),花 i 要放在花 j 的左边,如果i < j,每朵花放入每个花瓶有一个好看度(-50 <= Aij <= 50),求所有花放入花瓶后的最大好看度和. -->>设dp[i][j]表示将前j种花放入前i个花瓶的最大好看度和,则状态转移方程为: dp[i][j] = max(dp[i - 1][j], dp[i - 1][j -

POJ 1157 - LITTLE SHOP OF FLOWERS

据说是经典dp问题? 对于每个a[i][j],表示第 i 种花放在第 j 个花瓶里时产生的美学价值(aesthetic value), 我们用dp[i][j]表示共 i 种花放到 j 个花瓶里,产生的最大美学价值(显然这需要i<=j). 那么我们的答案也很简单,就是dp[F][V]. 那么接下来就是状态转移方程, 因为每个dp[i][j]:共 i 种花放到 j 个花瓶里,都有两种情况: ①第 i 种花放到第 j 个花瓶里,那么显然,前面的 i - 1 种花,就只能放到 j - 1 个瓶里,可以表

【插头DP】 POJ 1739 Tony&#39;s Tour

通道:http://poj.org/problem?id=1739 题意:左下角走到右下角路径数,单回路.做法就是我们新添2行后寻找回路就可以啦 . 代码: 1 #include <cstdio> 2 #include <cstring> 3 #include <algorithm> 4 5 using namespace std; 6 7 const int MAX_N = 13; 8 const int MAX_M = 13; 9 const int HASH =

poj 2411 Mondriaan&#39;s Dream 【dp】

题目:poj 2411 Mondriaan's Dream 题意:给出一个n*m的矩阵,让你用1*2的矩阵铺满,然后问你最多由多少种不同的方案. 分析:这是一个比较经典的题目,网上各种牛B写法一大堆.题解也是 我们可以定义状态:dp[i][st]:在第 i 行状态为 st 的时候的最大方案数. 然后转移方程:dp[i][st] = sum (dp[i-1][ss]) 即所有的当前行都是由上一行合法的状态转移而来. 而状态的合法性由两种铺法得到,第一种横放,注意要求前一行全满,然后竖放,上一行为空

【转】POJ题目分类

初级:基本算法:枚举:1753 2965贪心:1328 2109 2586构造:3295模拟:1068 2632 1573 2993 2996图:最短路径:1860 3259 1062 2253 1125 2240最小生成树:1789 2485 1258 3026拓扑排序:1094二分图的最大匹配:3041 3020最大流的增广路算法:1459 3436数据结构:串:1035 3080 1936排序:2388 2299哈希表和二分查找等高效查找法:3349 3274 2151 1840 2002

hdoj 2391 Filthy Rich 【DP】

题目大意:有个二维数组,你从(0,0)出发,最终到(n,m), 在这个二维数组中,每个位置dp[i][j]都有一定量的黄金,你可以拾取,问你最多能失去多少,并且,你的方向有下,右, 斜向下三个方向: 策略:就是每一个都加上它的上方向与左方向的最大值,这样到最后就是最大值.详情见代码 题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2391 代码: #include<stdio.h> #include<string.h> int dp[1

HDOJ1176 免费馅饼 【DP】+【经典数塔】

免费馅饼 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 23986    Accepted Submission(s): 8093 Problem Description 都说天上不会掉馅饼,但有一天gameboy正走在回家的小径上,忽然天上掉下大把大把的馅饼.说来gameboy的人品实在是太好了,这馅饼别处都不掉,就掉落在他身旁的1

【转】POJ 2492 A Bug&#39;s Life:基础并查集进阶

思路参考这里(较详细) 一开始总是WA调了一晚上原来···Init初始化写在scanf上面了···哎╮(╯▽╰)╭anyway!对并查集的理解更深了一步! #include<cstdio> #include<cstring> using namespace std; #define Size 2000 struct node { int Pre; int Relation;// 与父节点的关系 0同性 1异性 }Bug[Size+1]; int N, M; bool found;

nyoj 325 zb的生日 【DP】||【DFS】

两种方法: 第一种:将总数一半当做背包,用总数-2*最多能装的数目就是所求: 第二种:深搜: zb的生日 时间限制:3000 ms  |  内存限制:65535 KB 难度:2 描述 今天是阴历七月初五,acm队员zb的生日.zb正在和C小加.never在武汉集训.他想给这两位兄弟买点什么庆祝生日,经过调查,zb发现C小加和never都很喜欢吃西瓜,而且一吃就是一堆的那种,zb立刻下定决心买了一堆西瓜.当他准备把西瓜送给C小加和never的时候,遇到了一个难题,never和C小加不在一块住,只能