贪心算法之活动选择问题

 

/**

 * 活动选择之贪心解法

 * 在上周学习动态规划时已经用动态规划分析了活动选择,有:

 *   A[i][j] = A[i][k] ∪ {a[k]} ∪ A[k][j]

 *   c[i][j] = c[i][k] + 1 + c[k][j]

 * 将A[i][j]的解分解到两个子集(A[i][k]和A[k][j])的解,如果进一步分析:

 * 假设对于任意非空子集S[i][j],设a[m]是S[i][j]中具有最小结束时间的活动即:

 *     f[m] = min{f[k]: a[k] 属于S[i][j]}

 * 于是有新的结论:

 * 

 *    1.  活动a[m]在S[i][j]的某最大兼容活动子集中被使用

 *    2.  子问题S[i][m]为空,所以a[m]将使子问题S[m][j]为唯一可能非空的子问题

 *   简单证明一下:首先,假设S[i][m]为非空,可设a[k]属于S[i][m],有    s[i] <= s[k] < f[k] <= s[m] < f[m],这说明a[k]具有比a[m]更早的结束时间,这与a[m]的选择相矛盾

 *                其次,假设A[i][j]是Sij的最大兼容活动子集,且其元素按照结束时间排序,设a[k]是Aij第一个活动,若a[k]=a[m]则得到结论,

 *                      若a[k] != a[m],则可构造子集A'[i][j]=A[i][j] ∪ {a[m]} - a[k],因为A[i][j]中各活动兼容即A中的各个活动(除了a[k]子集本身)

 *                      的开始时间均比a[k]的结束时间大,而a[m]具有比a[k]更小的结束时间,所以在A中的各个活动(除了a[k])的开始时间也必定比a[m]的结束时间大

 *                      所以,A'[i][j]是兼容的,而A'与A具有相同个数的活动,故A'是包含a[m]的最大活动集合。

 *   所以我们只要每一步都选择结束时间最小的a[k]就可以,这就是贪心选择

 * @author song

 *

 */

代码就比动态规划解法简单多了:

public static List<Integer> greedySelectActivity(int[] s, int[] f, int n){
		List<Integer> result = new ArrayList<Integer>();
		result.add(1);
		int i = 1;
		for(int m = 2; m < s.length; ++m){
			if(s[m] >= f[i]){
				result.add(m);
				i = m;
			}
		}
		return result;
	}
 

 

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值