【洛谷P1230】智力大冲浪

题目大意:给定 N 项任务,每项任务有一个截至完成时间,若在截止时间之后完成要罚款 (w_i) 元,最初有 M 元,怎样完成能够留下最多得钱。

题解:按照罚款从多到少贪心,在查找能够最晚完成一项任务的时间时,可以采用并查集优化,即:建立一个时间上的并查集,每次在某个时间完成一项任务时,合并当前时间和前一个时间,这样每次查找时省去了一个循环的时间。

代码如下

#include <bits/stdc++.h>
using namespace std;
const int maxn=510;

int n,m,f[maxn];
struct node{int t,w;}e[maxn];
bool vis[maxn];

int find(int x){
	return x==f[x]?x:f[x]=find(f[x]);
}

bool cmp(const node& x,const node& y){
	return x.w>y.w;
}

void read_and_parse(){
	scanf("%d%d",&m,&n);
	for(int i=1;i<=n;i++)scanf("%d",&e[i].t);
	for(int i=1;i<=n;i++)scanf("%d",&e[i].w),f[i]=i;
	sort(e+1,e+n+1,cmp);
}

void solve(){
	for(int i=1;i<=n;i++){
		int fa=find(e[i].t);
		if(!fa)m-=e[i].w;
		else f[fa]=fa-1;
	}
	printf("%d
",m);
}

int main(){
	read_and_parse();
	solve();
	return 0;
} 
原文地址:https://www.cnblogs.com/wzj-xhjbk/p/10012270.html