434
社区成员
发帖
与我相关
我的任务
分享贪心策略分析
将数组升序排序后,从第一个程序开始选择,知道内存放不下下一个程序停止。
贪心算法:总是从可选程序中选择最小的试放入磁盘。
排序:对程序按大小升序排;
循环添加:从i = 1开始,选择排序后序列的第 i 个(即a[i],1 <= i <= n)个加入暂存(sum,初始为0),判断是否满足sum小于磁盘空间,是则计数(count++),否则跳出循环;
#include<iostream>
#include<algorithm>
using namespace std;
int main()
{
int n,l;
cin>>n>>l;
int *a = new int[n];
for(int i = 0;i<n;i++){
cin>>a[i];
}
sort(a,a+n);
int ct = 0;
for(int j = 0;j<n;j++){
if(l-a[j]>=0){
ct++;
l-=a[j];
}
else break;
}
cout<<ct;
return 0;
}
反证法证明贪心选择可以推出最优解:
证明选择可以从贪心(最小程序)开始:选择从最小程序开始即解不为空时可以选择最小程序。假设解不为空,从这样得到的选择序列中任选一个,用最小程序替换,放入程序数(count)不变;
证明最优子结构性质:在解不为空、第一次可以选择最小程序的前提下,假设在最优解中去掉第一次选择的最小程序后得到的子问题的最优解的count_0大于原问题最优解的count_1-1,那么将最小程序加入选择产生的解的count_2大于count_1,此时count_1不是最优解,这不成立。故此问题具有最优子结构性质。
时间复杂度:程序new了一个一维数组(a[n])用于存放每个程序的大小,故时间复杂度为O(n)。
贪心算法是指在对问题求解时,总是做出在当前看来是最好的选择。也就是说,不从整体最优上加以考虑,只做出在某种意义上的局部最优解。贪心算法不是对所有问题都能得到整体最优解,关键是贪心策略的选择,选择的贪心策略必须具备无后效性,即某个状态以前的过程不会影响以后的状态,只与当前状态有关。