HDU 5188 - zhx and contest (排序 + 背包)

题意

给出每个任务完成时候的最小时间,权,做任务的时间,求完成目标权值的最少时间。

思路

按l-t排序,这样排出来以后可以证明交换任务顺序结果不会变得更差(不会)。

好像背包写得有点不优雅跑了400ms。

代码

struct POINT
{
    int l, t, v;
    bool operator < (const POINT &a) const
    {
        return l-t < a.l-a.t;
    }
}p[MAXN];
 
int ans, maxTime, sum, remain[MAXN];
int n, w;
 
bool DFS(int curPos, int curTime, int curSum, int limit)
{
    if (curTime > ans || curTime > limit) return false;
    if (curSum >= w) return true;
    if (curPos == n) return false;
    if (curSum + remain[curPos] < w) return false;
    if (DFS(curPos+1, max(curTime+p[curPos].t, p[curPos].l), curSum+p[curPos].v, limit)) return true;
    if (DFS(curPos+1, curTime, curSum, limit)) return true;
    return false;
}
 
int Solve()
{
    int l = 0, r = INF;
    while (l < r)
    {
        int mid = MID(l, r);
        if (DFS(0, 0, 0, mid)) ans = r = mid;
        else l = mid+1;
    }
    return ans;
}
 
int main()
{
    //ROP;
    while (~scanf("%d%d", &n, &w))
    {
        sum = 0, maxTime = 0, ans = INF;
        for (int i = 0; i < n; i++)
        {
            scanf("%d%d%d", &p[i].t, &p[i].v, &p[i].l);
            sum += p[i].v;
        }
        if (sum < w)
        {
            puts("zhx is naive!");
            continue;
        }
        LL add = 0;
        for (int i = 0; i < n; i++) remain[i] = sum-add, add += p[i].v;
        sort(p, p+n);
        printf("%d\n", Solve());
    }
    return 0;
}

Powered by Jekyll and Theme by solid