问题 C: 工作(dp)
题目描述
这次故事的主角是HG!转眼4年过去了,HG本科毕业了,于是找了份工作。每天HG会收到一份任务清单,清单上列出了n个可能需要他完成的任务。每个任务包含3个信息:Ti、Ai、Bi,Ti表示完成此任务需要的时间,Ai表示此任务的到达时间,Bi表示此任务的最晚完成时间。在某一时刻若HG手上没有任务,那么他可以选择一个已经到达且还能够在Bi时刻之前(或者恰好在Bi时刻)完成的任务来做。
由于HG有点懒(纯属虚构:D),他想尽量少的减少他的总工作时间,但是他不能在可以做任务的时候故意不做(这样会被炒鱿鱼的>_<),那么他该如何挑选任务来做呢?
你的任务就是求出HG的最少工作时间(即总共有多少时间HG在做任务)。
由于HG有点懒(纯属虚构:D),他想尽量少的减少他的总工作时间,但是他不能在可以做任务的时候故意不做(这样会被炒鱿鱼的>_<),那么他该如何挑选任务来做呢?
你的任务就是求出HG的最少工作时间(即总共有多少时间HG在做任务)。
输入
第一行一个整数n表示任务数。
以下n行,每行三个整数Ti,Ai,Bi。(n<=1000,0<=Ai,Bi<=1500,Ti>=1)
以下n行,每行三个整数Ti,Ai,Bi。(n<=1000,0<=Ai,Bi<=1500,Ti>=1)
输出
输出仅一个数,即最少工作时间。
样例输入 Copy
3
15 0 25
50 0 90
45 15 70
样例输出 Copy
50
提示
Ti>=1,0<=Ai,Bi<=1200;
30%的数据满足n<=5;
60%的数据满足n<=500;
100%的数据满足n<=1000。
输入数据保证Bi-Ai要大于等于Ti,且小于2Ti。
30%的数据满足n<=5;
60%的数据满足n<=500;
100%的数据满足n<=1000。
输入数据保证Bi-Ai要大于等于Ti,且小于2Ti。
思路:dp,起点时间开始到中点时间。dp[i+a[j]]=min(dp[i]+a[j],dp[i+a[j]]);
#pragma comment(linker, "/STACK:1024000000,1024000000")
#pragma GCC optimize(3,"Ofast","inline")
#include <bits/stdc++.h>
#include <stdio.h>
#include <iostream>
#include <cstdlib>
#include <cmath>
#include <cctype>
#include <string>
#include <cstring>
#include <algorithm>
#include <stack>
#include <queue>
#include <set>
#include <map>
#include <ctime>
#include <vector>
#include <fstream>
#include <list>
#include <iomanip>
#include <numeric>
using namespace std;
#define rep(i , a , b) for(register int i=(a);i<=(b);i++)
#define per(i , a , b) for(register int i=(a);i>=(b);i--)
#define ms(s) memset(s, 0, sizeof(s))
#define squ(x) x*x;
typedef long long ll;
typedef unsigned long long ull;
typedef pair<int ,int> pi;
typedef unordered_map<int,int> un_map;
template<class T>
inline void read (T &x) {
x = 0;
int sign = 1;
char c = getchar ();
while (c < '0' || c > '9') {
if ( c == '-' ) sign = - 1;
c = getchar ();
}
while (c >= '0' && c <= '9') {
x = x * 10 + c - '0';
c = getchar ();
}
x = x * sign;
}
const int maxn = 1e6 + 10;
const int inf = 0x3f3f3f3f;
const ll INF = ll(1e18);
const int mod = 1e9+7;
const double PI = acos(-1);
#define LOCAL
struct node
{
int t;
int a,b;
}e[maxn];
int n;
ll dp[maxn];
void solve() {
int st = inf,ed = -inf;
rep(i,1,n) {
read(e[i].t);read(e[i].a);read(e[i].b);
st=min(st,e[i].a);
ed=max(ed,e[i].b);
}
rep(i,st,ed) dp[i]=inf;
dp[st]=0;
rep(i,st,ed) {
int f=0;
rep(j,1,n) {
if(i>=e[j].a&&i+e[j].t<=e[j].b) {
f=1;
dp[i+e[j].t]=min(dp[i]+e[j].t,dp[i+e[j].t]);
//cout<<dp[i+e[j].t]<<' '<<i<<' '<<j<<endl;
}
}
//cout<<dp[i]<<' '<<i<<endl;
if(!f) dp[i+1]=min(dp[i],dp[i+1]);
}
printf("%lld\n", dp[ed]);
}
int main(int argc, char * argv[])
{
//freopen("/home/yesky/桌面/date.in", "r", stdin);
//freopen("/home/yesky/桌面/date.out", "w", stdout);
while(~scanf("%d",&n)) {
solve();
}
return 0;
}