家庭作业

https://loj.ac/problem/10008

题目描述

  有(n)个任务,每个任务都有完成时间和完成奖励,求最大的完成奖励。

思路

  这道题的贪心策略与智力大冲浪相类似,就不再赘述了。主要讲优化。智力大冲浪这道题的数据比较水,(Ο(n^2))的复杂度都能过。但这里显然过不去,那么就考虑优化。首先扫一遍任务是必需花费,不可减少,就考虑从寻找最近可安排时刻进行优化。我们可以用并查集来维护无效区间,每次只需要往前跳就行了。当然用链表维护也可以。

代码

#pragma GCC optimize(3)
#include <bits/stdc++.h>
using namespace std;
struct aa
{
    int d,v;
    bool operator < (const aa &x)const
    {
        return v<x.v;
    }
}a;
priority_queue<aa>q;
int fa[710000];
bool cmp(aa x,aa y)
{
    return x.v>y.v;
}
int read()
{
    char ch=getchar();
    int ret=0,w=1;
    while(ch<'0'||ch>'9'){if(ch=='-')w=-1;ch=getchar();}
    while(ch>='0'&&ch<='9'){ret=ret*10+ch-'0';ch=getchar();}
    return ret*w;
}
int find(int x)
{
    return fa[x]==x?x:fa[x]=find(fa[x]);
}
int main() 
{
    int n,maxx=0;
    n=read();
    for(int i=1;i<=n;++i)
    {
        a.d=read(),a.v=read();
        q.push(a);
        maxx=max(a.d,maxx);
    }
    for(int i=1;i<=maxx;i++)
        fa[i]=i;
    int ans=0;
    for(int i=1;i<=n;++i)
    {
        int flag=0;
        a=q.top();q.pop();
        if(find(a.d))
        {
            ans+=a.v;
            fa[fa[a.d]]=find(fa[fa[a.d]]-1);
        }
    }
    printf("%d",ans);
    return 0;
}
原文地址:https://www.cnblogs.com/fangbozhen/p/11754229.html