CF639E Bear and Paradox 题解
题面(带翻译)戳这里
算法:贪心
二分\(c\),考虑如何check
首先,利用邻项交换的方法,可以证明最终的方案一定是按\(\frac{p_i}{t_i}\)排序的序列
简单证明如下
设\(p_i\)在\(x+t_i\)时刻完成,\(p_{i+1}\)在\(x+t_i+t_{i+1}\)时刻完成
则\(p_i\)在\(p_{i+1}\)前面的充要条件是\(p_i(1-\frac{c(x+t_i)}{T})+p_{i+1}(1-\frac{c(x+t_i+t_{i+1})}{T})-p_{i+1}(1-\frac{c(x+t_{i+1})}{T})-p_{i}(1-\frac{c(x+t_i+t_{i+1})}{T})>0\)
化简一下就可以得到上面的式子
这可以在二分之前先排序
由于是所有情况都要满足,我们只要分析最坏的情况即可
对于每个问题,最早完成时间就是它在这一"段"中最早执行的时间,最晚完成时间就是它在这一"段"中最晚完成的时间
这里"段"指的是\(\frac{p_i}{t_i}\)相同的连续的一段问题组成的集合
那么能完成问题的条件就是对于任意\(p_i>p_j\),\(i\)在最晚完成时间的分数严格大于\(j\)在最早时间完成的分数
排序可以在二分之前先排
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
using namespace std;
double eps = 1e-8;
const int N = 200005;
double ear[N],sum[N],lat[N];
double minn[N];
int n,pre[N];
inline int read() {
int x=0,f=1;
char ch=getchar();
while(ch<'0'||ch>'9') {
if(ch=='-')
f=-1;
ch=getchar();
}
while(ch>='0'&&ch<='9') {
x=(x<<1)+(x<<3)+(ch^48);
ch=getchar();
}
return x*f;
}
struct pro{
int p,t,id;
double now;
}a[N];
bool cmp(pro u,pro v) {
return u.now > v.now;
}
bool cmp2(pro u,pro v) {
return u.p > v.p;
}
bool check(double mid) {
for(int i = 1;i <= n;i++) {
double nw = a[i].p*(1-ear[a[i].id]*mid/sum[n]);
if(nw > minn[pre[i]]) return false;
minn[i] = min(minn[i-1],a[i].p*(1-lat[a[i].id]*mid/sum[n]));
}
return true;
}
int main () {
minn[0] = 0x3f3f3f3f;
n = read();
for(int i = 1;i <= n;i++) {
a[i].p = read();
}
for(int i = 1;i <= n;i++) {
a[i].t = read();
a[i].now = 1.0*a[i].p/a[i].t;
}
sort(a+1,a+n+1,cmp);
for(int i = 1;i <= n;i++) {
sum[i] = sum[i-1] + a[i].t;
a[i].id = i;
}
for(int i = 1;i <= n;i++) {
for(int j = i;j <= n+1;j++) {
if(a[j].now != a[i].now||j > n) {
for(int k = i;k < j;k++) {
ear[k] = sum[i-1] + a[k].t;
lat[k] = sum[j-1];
}
i = j-1;
break;
}
}
}
sort(a+1,a+n+1,cmp2);
for(int i = 1;i <= n;i++) {
for(int j = i;j <= n+1;j++) {
if(a[j].p != a[i].p||j > n) {
for(int k = i;k < j;k++) {
pre[k] = i-1;
}
i = j-1;
break;
}
}
}
double l = 0,r = 1;
while(r - l > eps) {
double mid = (l + r) / 2;
if(check(mid)) {
l = mid;
}
else r = mid;
}
printf("%.6lf\n",l);
return 0;
}

浙公网安备 33010602011771号