贪心算法通常是对某一值进行排序,然后再采取贪心策略进行求解。此问题贪心角度不同以往,它是对两因素进行综合处理。将它们的乘积进行排序。
题意:设有n 个程序{1,2,…, n }要存放在长度为L的磁带上。程序i存放在磁带上的长度是Li, 1<= i<= n。这n 个程序的读取概率分别是p1,p2,...,pn,且pi+p2+...+pn = 1。如果将这n 个程序按 i1,i2,....,in 的次序存放,则读取程序tr 所需的时间tr=c*(Pi1*Li1+Pi2*Li2+...+Pir*Lir)。(每到第n个程序就要计算第一个程序到第n个程序的时间)这n 个程序的平均读取 时间为t1+t2+...+tn。(前面各阶段计算的时间总和) 。磁带最优存储问题要求确定这n 个程序在磁带上的一个存储次序,使平均读取时间达到 最小。试设计一个解此问题的算法,并分析算法的正确性和计算复杂性。 编程任务: 对于给定的n个程序存放在磁带上的长度和读取概率,编程计算n个程序的最优存储方 案。
代码:
/**
@贪心算法-磁带优化存储问题
@ author-狂热的coder
*/
#include<iostream>
#include<algorithm>
#define MAX 1000
using namespace std;
typedef struct Tnode{
int len; //长度
int pr; //概率
}Tnode,tnode[MAX];
bool cmp(Tnode a,Tnode b){ //根据长度与概率值的乘积排序
int x = a.len*a.pr,y = b.len*b.pr;
return x<y;
}
void minTimeCost(int n,tnode t){
int sum = 0;
for(int i = 0;i<n;i++){
sum+=t[i].pr; //总读取概率值
}
double result;
for(int i = 0;i<n;i++){
for(int j = 0;j<=i;j++){ //每一阶段的读取时间
result+=t[j].pr*1.0/sum*t[j].len;
}
}
cout<<"最小平均读取时间为: "<<result<<endl;
}
int main(){
int n;
cout<<"输入程序个数:"<<endl;
cin>>n;
tnode t;
cout<<"输入各程序的长度和读取概率:"<<endl;
for(int i = 0;i<n;i++){
cin>>t[i].len>>t[i].pr;
}
sort(t,t+n,cmp);
minTimeCost(n,t);
return 0;
}
/*
5
71 872
46 452
9 265
73 120
35 85
排序后:
9 265
35 85
73 120
46 452
71 872
*/