zoukankan      html  css  js  c++  java
  • Blue Mary开公司

    Blue Mary开公司

    题面:[JSOI2008]Blue Mary开公司

    题目大意:

    每次加入一条形如 \(y=Px + S - P\) 的直线,询问 \(x=T\) 时此处最高的 \(y\) 值(\(S,P,T\)均为题中给出)

    思路

    很经典的李超树模板, 每次在整个线段树中加入一条直线
    注意:每天最小收益至少为 \(0\)!!
    即你的答案必然不小于 \(0\) !!
    不会李超树的戳这里:李超树学习笔记

    \(Code\)

    #include<cstdio>
    #include<cmath>
    using namespace std;
    
    const int T = 50010;
    int n , fl[4 * T];
    
    struct tree{
    	double k , b;
    }seg[4 * T];
    
    inline double max(double x , double y){return x < y ? y : x;}
    inline double Intersection(double k1 , double b1 , double k2 , double b2){return 1.0 * (b2 - b1) / (k1 - k2);}
    
    inline void update(double k , double b , int l , int r , int rt)
    {
    	if (!fl[rt])
    	{
    		seg[rt].k = k , seg[rt].b = b , fl[rt] = 1;
    		return;
    	}
    	double f1 = seg[rt].k * l + seg[rt].b , f2 = seg[rt].k * r + seg[rt].b;
    	double f3 = k * l + b , f4 = k * r + b;
    	if (f1 >= f3 && f2 >= f4) return;
    	else if (f1 <= f3 && f2 <= f4) seg[rt].k = k , seg[rt].b = b;
    	else{
    		int mid = (l + r) >> 1;
    		double len = Intersection(k , b , seg[rt].k , seg[rt].b);
    		if (f1 <= f3)
    		{
    			if (len <= mid) update(k , b , l , mid , rt << 1);
    			else update(seg[rt].k , seg[rt].b , mid + 1 , r , rt << 1 | 1) , seg[rt].k = k , seg[rt].b = b;
    		}
    		else {
    			if (len > mid) update(k , b , mid + 1 , r , rt << 1 | 1);
    			else update(seg[rt].k , seg[rt].b , l , mid , rt << 1) , seg[rt].k = k , seg[rt].b = b;
    		}
    	}
    }
    
    inline double query(int l , int r , int rt , int x)
    {
    	double ans = 1.0 * seg[rt].k * x + seg[rt].b;
    	if (l == r) return ans;	
    	int mid = (l + r) >> 1;
    	if (x <= mid) ans = max(ans , query(l , mid , rt << 1 , x));
    	else ans = max(ans , query(mid + 1 , r , rt << 1 | 1 , x));
    	return ans;
    }
    
    int main()
    {
    	char s[10];
    	double b , k;
    	int x;
    	scanf("%d" , &n);
    	for(register int i = 1; i <= 4 * 50005 + 1; i++) seg[i].b = -1e18 , seg[i].k = 0;
    	while(n--)
    	{
    		scanf("%s" , s + 1);
    		if (s[1] == 'P')
    		{
    			scanf("%lf %lf" , &b , &k);
    			b = b - k;
    			update(k , b , 1 , 5e4 + 5 , 1);
    		}
    		else {
    			scanf("%d" , &x);
    			double ans = query(1 , 5e4 + 5 , 1 , x);
    			if (ans <= 0) printf("0\n");
    			else printf("%d\n" , (int)(ans / 100));
    		}
    	}
    }
    
  • 相关阅读:
    PHP之旅3 php数组以及遍历数组 以及each() list() foreach()
    NSSetUncaughtExceptionHandler
    runtime
    Objective-C中的instancetype和id区别
    tableView 局部刷新
    CGAffineTransform
    iOS中文本属性Attributes
    ios 相机 自定义 相片的截取
    php程序的生命周期
    PHP代码执行流程
  • 原文地址:https://www.cnblogs.com/leiyuanze/p/13375417.html
Copyright © 2011-2022 走看看