贪心算法之区间调度问题

                                               

分析:

拿到这道题目,首先要看清楚最终的题目要求,它的要求是参与尽可能多的工作,并不是说工作总时间最长。

对于这题我们其实可以使用贪心算法,就是不断选取当前最优策略

我们不断选取工作,其实可以有以下几种思路进行选取,并进行聚反例来排除这种思路:

1.在可选的工作中,选取开始时间最早的.

反例:

       

这种情况下先根据开始最早原则选取3号工作,这样剩下的1,2工作都不能被选取,而我们明显可以看到如果1,2工作,其工作数量是只比选取1号工作多的------不可取

2.在可选的工作中,选取用时最短的的:

反例:

      

这种情况下按照用时最短的原则选取,先选3,那么剩下的1,2都无法选取,和第一种情况是一样的,还不如选取1,2工作更满足题意------不可取

3.在可选的工作中选取与其他可选工作重叠最少的工作:

反例:

  

先选取5号工作,之后依次选取1和4,明显不对,我们有一种更符合的情况,那就是1,2,3,4-------不可取

4.在可选的工作中,选取结束时间最早的工作:

最终我们用的就是这种情况,并没有反例,我也确实找了好久没有找到。对于这种思路,大家可以想想,结束的时间越早,那么剩余的供选择的时间范围也就更广。

源代码:

#include<iostream>
#include<algorithm>
#include<cstdlib>
using namespace std;
#define Max_N 100000
//int start[Max_N];
//int end[Max_N];
int n;
pair<int,int> p[Max_N];
int main()
{
	cin>>n;
	for(int i=0;i<n;i++)
	{
		int start,end;
	   cin>>start>>end;
       p[i]=make_pair(end,start);	
	}                               //输入数据,并组成pair对保存在数组中 
	sort(p,p+n);                     //按照pair中第一个关键词进行升序排序 
	
	int last=0,ans=0;
	cout<<"选择的工作的起始时间有:"<<endl;
	for(int i=0;i<n;i++)
	{
		if(p[i].second>last)             //现在寻找的下一个工作的开始时间大于上一次工作的结束时间,则选择该次工作 
		  {
		    last=p[i].first;
		    ans++;
		    cout<<p[i].second<<"--"<<p[i].first<<endl;
		  }
	}
	cout<<"共选择了 "<<ans<<" 个工作";
	return 0;
}

PS:这次选择了使用截图的方式,直接将题目用截图的方式展示出来,省去了之前手敲题目的繁杂,也可以让我将更多的精力放在代码研究和思路探索与方案分析上,以后本系列的博文也会采取这种方式~

  • 1
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值