码迷,mamicode.com
首页 > 其他好文 > 详细

P1230 智力大冲浪

时间:2020-04-06 21:03:56      阅读:81      评论:0      收藏:0      [点我收藏+]

标签:bool   getch   ace   +=   贪心   任务   i++   stream   跳过   

智力大冲浪

翻了翻题解发现没有并查集解法(眼瞎勿怪),于是水一发题解。(貌似跑得比某些题解快)

首先肯定是尽量做减少价格大的任务,所以就按照价值从大到小排个序。

然后就有并查集的玄学操作了:

  1. 找到商品 \(i\) 的祖先 \(find(i)\)
  2. 倘若 \(find(i)!=0\) ,加上 \(i\) 的价值,合并 \(find(i)\)\(find(find(i)-1)\)
  3. 否则跳过。

其实这里的并查集维护的是 \(i\) 能插入的最晚时间,显然每次插入应尽量插入到最晚的时间,所以符合贪心。

最坏时间复杂度:\(O(nlogn)\)

#include<cstdio>
#include<algorithm>
#include<cmath>
#include<cstring>
#include<iostream>
#define N 510
using namespace std;

int M,n,fa[N];
struct node{
	int t,c;
}a[N];

int read(){
	int x=0,f=1;char c=getchar();
	while(c<‘0‘ || c>‘9‘) f=(c==‘-‘)?-1:1,c=getchar();
	while(c>=‘0‘ && c<=‘9‘) x=x*10+c-48,c=getchar();
	return x*f;
}

bool cmp(node a,node b){
	if(a.c!=b.c) return a.c>b.c;
	return a.t>b.t;
}

int find(int x){
	if(fa[x]==x) return x;
	return fa[x]=find(fa[x]);
}

int main(){
	M=read();n=read();
	for(int i=1;i<=n;i++) a[i].t=read();
	for(int i=1;i<=n;i++) a[i].c=read();
	for(int i=1;i<=n;i++) fa[i]=i;
	sort(a+1,a+n+1,cmp);
	int ans=0;
	for(int i=1;i<=n;i++){
		int f=find(a[i].t);
		if(f<1) ans+=a[i].c;
		else fa[f]=find(f-1);
	}
	printf("%d\n",max(0,M-ans));
	return 0;
}

P1230 智力大冲浪

标签:bool   getch   ace   +=   贪心   任务   i++   stream   跳过   

原文地址:https://www.cnblogs.com/lpf-666/p/12643974.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!