zoukankan      html  css  js  c++  java
  • Codeforces 1083E The Fair Nut and Rectangles

    Description

    (N)个左下定点为原点的矩阵, 每个矩阵((x_i,~y_i))都有一个数(a_i)表示其花费。

    没有一个矩阵包含另一个矩阵。

    现要你选出若干个矩阵, 使得矩阵组成的图形的大小减去总花费得到的数最大

    Solution

    先按照(x_i) 递增排序, 由于矩阵互不包含, 所以(y_i)递减。 就可以列出(DP)方程:

    [f_i~=~(x_i~-~x_j)~ imes~ y_i~-~a_i~+~f_j~~~~~~~~(j<i) ]

    可以拆成斜率优化方程:

    [f_j~=~y_i~ imes~x_j~+~a_i~-~x_i~ imes~y_i~+~f_i ]

    上斜率优化板子就AC了, 复杂度(O(N))

    Code

    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<cmath>
    #include<vector>
    #define up(a, b) (a = a > b ? a : b)
    #define down(a, b) (a = a > b ? b : a)
    #define cmax(a, b) (a > b ? a : b)
    #define cmin(a, b) (a > b ? b : a)
    #define Abs(a) ((a) > 0 ? (a) : -(a))
    #define rd read()
    #define db double
    #define LL long long
    using namespace std;
    typedef pair<int, int> P;
    
    inline char nc(){
        static char buf[1<<14],*p1=buf,*p2=buf;
        return (p1==p2)&&(p2=(p1=buf)+fread(buf,1,1<<14,stdin),p1==p2)?EOF:*p1++;
    }
    inline LL read(){
        char c=nc();LL x=0,f=1;
        while(c<'0'||c>'9'){if(c=='-')f=-1;c=nc();}
        while(c>='0'&&c<='9'){x=x*10+c-'0',c=nc();}
        return x*f;
    }
    
    const int N = 1e6 + 1e5;
    
    int n, q[N];
    LL ans = 0, f[N];
    
    struct node {
    	int x, y;
    	LL w;
    	bool operator < (const node &b) const {
    		return x < b.x;
    	}
    }a[N];
    
    double calk(int A, int B) {
    	double ax = a[A].x, bx = a[B].x;
    	double ay = f[A], by = f[B];
    	return (ay - by) / (ax - bx);
    }
    
    int main()
    {
    	n = rd;
    	for (int i = 1; i <= n; ++i) {
    		a[i].x = rd;
    		a[i].y = rd;
    		a[i].w = rd;
    	}	
    	sort(a + 1, a + 1 + n);
    	int l = 1, r = 1;
    	for (int i = 1; i <= n; ++i) {
    		while (l < r && calk(q[l], q[l + 1]) >= a[i].y)
    			l++;
    		int tmp = q[l];
    		f[i] = (1LL * a[i].x - a[tmp].x) * a[i].y - a[i].w + f[tmp];
    		up(ans, f[i]);
    		while (l < r && calk(q[r], q[r - 1]) <= calk(q[r], i))
    			r--;
    		q[++r] = i;
    	}
    	printf("%lld
    ", ans);
    }
    
  • 相关阅读:
    用Python证明“真理再前进一步就是谬误”
    senior developer in Hongkong
    Emacs 维基百科,自由的百科全书
    深入C(和C++)
    图灵等价和图灵完备
    2012年中国大陆和香港的工资收入水平市场调查报告
    图灵完备
    linux中vi进行字符替换_井底之蛙_百度空间
    they're hiring
    Linux下游戏大作赏析(三)
  • 原文地址:https://www.cnblogs.com/cychester/p/10181705.html
Copyright © 2011-2022 走看看