题意: 给奶牛挤奶,共有n小时,有m次可以挤,给出每次开始挤奶的时间s,结束挤奶的时间e,还有挤奶的量f,每次挤完奶要休息r时间,问最大挤奶量.
有两种思路,
一. LIS的变形,
dp[i]表示以第i个节点结尾的最优解
1. dp[i]有两种情况,第一是的max(dp[i],d[i].f),第二就是max(dp[i],dp[j]+d[i].f),我刚开始以为if (d[i].s >= d[j].e + r) ,就是max(dp[i],dp[j]+d[i].f),else就是max(dp[i],d[i].f),其实不是这样。因为第二层循环不会刷新dp[0],所以如果dp[1]没有使用dp[0],那么d[0]的数据就会被省略,造成错误,非要这么写的话,应该在最前面对dp[0]赋值。
2. 我刚开始以为直接输出dp[m-1],dp数组的定义是以第i个节点结尾的最佳解,所以真正的最佳解有可能在中间,
#include <iostream>
#include <cstdio>
#include <iomanip>
#include <string>
#include <cstdlib>
#include <cstring>
#include <queue>
#include <set>
#include <vector>
#include <map>
#include <algorithm>
#include <cmath>
#include <stack>
#include <stdlib.h>
#include <stdio.h>
#define INF 0x3f3f3f3f
#define LINF 0x3f3f3f3f3f3f3f3f
#define ll long long
#define ull unsigned long long
#define uint unsigned int
#define l(x) (x<<1)
#define r(x) (x<<1|1)
#define ms(a,b) memset(a,b,sizeof(a))
using namespace std;
struct node {
int s, e,f;
friend bool operator<(const node&a, const node&b) {
return a.s < b.s;
}
};
int n, m, r,len,res;
node d[1111111];
int dp[1111111];
int main() {
ios::sync_with_stdio(false);
cin >> n >> m >> r;
for (int i = 0; i < m; i++) {
cin >> d[i].s>> d[i].e>> d[i].f;
}
sort(d, d + m);
ms(dp, 0);
//for(int i = 0; i < m; i++) dp[i] = d[i].f;
dp[0] = d[0].f;
for (int i = 0; i < m; i++) {
for (int j = 0; j < i; j++) {
if (d[i].s >= d[j].e + r) {
dp[i] = max(dp[i], dp[j] + d[i].f);
}
else {
dp[i] = max(dp[i], d[i].f);
}
}
res = max(res, dp[i]);
}
cout << res << endl;
return 0;
}
二.普通的dp
dp[i]表示i时刻的最优解
- 上面出现的问题,
- 对于node的排序,应该是结束时间排序,而不是开始时间排序
#include <iostream>
#include <cstdio>
#include <iomanip>
#include <string>
#include <cstdlib>
#include <cstring>
#include <queue>
#include <set>
#include <vector>
#include <map>
#include <algorithm>
#include <cmath>
#include <stack>
#include <stdlib.h>
#include <stdio.h>
#define INF 0x3f3f3f3f
#define LINF 0x3f3f3f3f3f3f3f3f
#define ll long long
#define ull unsigned long long
#define uint unsigned int
#define l(x) (x<<1)
#define r(x) (x<<1|1)
#define ms(a,b) memset(a,b,sizeof(a))
using namespace std;
struct node {
int s, e,f;
friend bool operator<(const node&a, const node&b) {
return a.e < b.e;
}
};
int n, m, r,len,res;
node d[1111111];
int dp[1111111];
int main() {
ios::sync_with_stdio(false);
cin >> n >> m >> r;
for (int i = 0; i < m; i++) {
cin >> d[i].s>> d[i].e>> d[i].f;
}
sort(d, d + m);
ms(dp, 0);
for(int i = 0; i < m; i++) dp[d[i].e] = d[i].f;
len = 0;
for (int i = 0; i <= n; i++) {
dp[i] = dp[i - 1];
for (; len < m && d[len].e <= i; len++)
if (i > r)
dp[i] = max(dp[i], dp[d[len].s - r] + d[len].f);
else
dp[i] = max(dp[i], d[len].f);
res = max(res, dp[i]);
}
cout << res << endl;
return 0;
}