1. 程式人生 > >poj 3616 奶牛產奶問題 dp算法

poj 3616 奶牛產奶問題 dp算法

node 一個 sin algorithm pre 安排 turn memset amp

題意:奶牛產奶,農夫有m個時間段可以擠奶,在工作時間 f t 內產奶量為m,每次擠完奶後,奶牛需要休息R。問:怎麽安排使得產奶量最大?

思路:區間dp dp[i]表示第i個時段

  1. 對農夫工作的結束時間由小到大排序
  2. 將第i時段 如果前面與其不沖突記錄下來 inter[k].e+r>inter[i].b 表示沖突
  3. 遞推公式 dp[i]=max(dp[i-],dp[p[i]]+inter[i].w) 前面一個表示不作為,後面一個表示選取上一個不沖突的時間+這次的產奶量

解決問題的代碼:

#include <iostream>
#include <cstdio>
#include 
<string.h> #include <algorithm> using namespace std; struct node { int b, e, w; }inter[1010]; int dp[1010], p[1010]; int cmp(node a, node b) { return a.e < b.e; } void dix(int m, int r) { for (int i = m - 1; i >= 0; i--) { int k = i - 1; while (k >= 0 && (inter[k].e + r > inter[i].b)) k
--; p[i] = k; } } int main() { int n, m, r; scanf("%d%d%d", &n, &m, &r); for (int i = 0; i < m; i++) scanf("%d%d%d", &inter[i].b, &inter[i].e, &inter[i].w); memset(dp, 0, sizeof(dp)); sort(inter, inter + m, cmp); dix(m, r); for
(int i = 0; i < m; i++) dp[i] = max(dp[i - 1], dp[p[i]] + inter[i].w); printf("%d\n", dp[m - 1]); return 0; }

poj 3616 奶牛產奶問題 dp算法