http://poj.org/problem?id=1064
#include<stdio.h>
#include<string.h>
#include<iostream>
#include<algorithm>
#include<queue>
#include <time.h>
#include<math.h>
using namespace std;
double key[10010];
double maxn;
int n,k;
double l,r;
bool C(double x)//判断解是否可行
{
int sum=0;
for(int i=0;i<n;i++)
{
sum+=(int)(key[i]/x);
}
if(sum>=k)return true;
return false;
}
void Binary()
{
l=0,r=maxn;
for(int i=1;i<=100;i++)//100次循环可以使精度达到1e-30; 除此以外还可以把终止条件设为(R-L)<EPS这样,在这种情况下如果EPS取得太小了,就有可能因为浮点小数的精度的原因导致陷入死循环
{
double mid=(l+r)/2.0;
if(C(mid))l=mid;
else r=mid;
}
}
int main()
{
scanf("%d%d",&n,&k);
maxn=0;
for(int i=0;i<n;i++)
{
scanf("%lf",&key[i]);
if(key[i]>maxn)
maxn=key[i];
}
Binary();
printf("%.2lf\n",floor(r*100)/100);// 它会进位printf("%.2lf",r);---------
}
最大化最小值
http://poj.org/problem?id=2456
#include<stdio.h>
#include<string.h>
#include<iostream>
#include<algorithm>
#include<queue>
#include <time.h>
#include<math.h>
using namespace std;
int n,m;
int key[100010];
int maxn=0;
int l,r;
bool C(int x)
{
int last=0;
for(int i=1;i<m;i++)
{
int crt=last+1;
while(crt<n&&key[crt]-key[last]<x)
crt++;
if(crt==n)return false;
last=crt;
}
return true;
}
void Binary()
{
l=0,r=maxn;
while(r-l>1)//l和r都为整数,所以循环结束的条件为while(r-l>1)
{
int mid=(l+r)/2;
if(C(mid))l=mid;
else r=mid;
}
printf("%d\n",l);
}
int main()
{
scanf("%d%d",&n,&m);
for(int i=0;i<n;i++)
{
scanf("%d",&key[i]);
if(key[i]>maxn)
maxn=key[i];
}
sort(key,key+n);
Binary();
return 0;
}
最大化平均值
http://poj.org/problem?id=3111
//从中选出前k个物品使得单位重量的价值最大,假设x为单位重量的价值最大,则v[i]/w[i]>=x<<==>>v[i]-x*w[i]>=0;
#include<stdio.h>
#include<string.h>
#include<iostream>
#include<algorithm>
#include<queue>
#include <time.h>
#include<math.h>
using namespace std;
int n,k;
struct node
{
double vi;//价值
double wi;//重量
double y;//记录v[i]-w[i]*x;
int r;//记录位置
}key[100010];
double l,r;
double maxn;
bool cpp(node x,node y)
{
return x.y>y.y;
}
bool C(double x)
{
for(int i=0;i<n;i++)
{
key[i].y=key[i].vi-key[i].wi*x;
}
sort(key,key+n,cpp);
double sum=0;
for(int i=0;i<k;i++)
{
sum+=key[i].y;
}
return sum>=0;
}
void Binary()
{
double l=0,r=maxn;
while(r-l>=1e-8)//for(int i=0;i<100;i++)是能使精度达到1e-30这么大,但是超时了,还是要看范围
{
double mid=(l+r)/2.0;
if(C(mid))l=mid;
else r=mid;
}
for(int i=0;i<k-1;i++)
{
printf("%d ",key[i].r);
}
printf("%d\n",key[k-1].r);
}
int main()
{
scanf("%d%d",&n,&k);
maxn=0;
for(int i=0;i<n;i++)
{
scanf("%lf%lf",&key[i].vi,&key[i].wi);
key[i].r=i+1;
if(maxn<key[i].vi/key[i].wi)
maxn=key[i].vi/key[i].wi;
}
Binary();
}