• 覆盖的面积 HDU


    题意:

     就是扫描线求面积交

    解析:

      参考求面积并。。。。 就是把down的判断条件改了一下。。由w > 0 改为 w > 1 同时要讨论一下 == 1 时  的情况, 所以就要用到一个临时的sum。。

    具体看代码把

    #include <iostream>
    #include <cstdio>
    #include <sstream>
    #include <cstring>
    #include <map>
    #include <set>
    #include <vector>
    #include <stack>
    #include <queue>
    #include <algorithm>
    #include <cmath>
    #define MOD 2018
    #define LL long long
    #define ULL unsigned long long
    #define Pair pair<int, int>
    #define mem(a, b) memset(a, b, sizeof(a))
    #define _  ios_base::sync_wity_stdio(0),cin.tie(0)
    //freopen("1.txt", "r", stdin);
    using namespace std;
    const int maxn = 2010, INF = 0x7fffffff;
    double X[maxn];  //记录x的坐标
    
    struct node{
        int l, r;  // 线段树的左右端点
        int w;     // 记录边重叠的情况
        double lx, rx, sum, lsum; //sum代表当前区间线段的长度,lx和rx为线段的真实端点
    
    }Node[maxn*3];
    
    struct edge{
        double lxx, rxx, y; // 存储边的左右端点和y
        int f;    //标记是下边还是上边 (下边为1 上边为-1)
    }Edge[maxn];
    
    int cmp(edge a, edge b)
    {
        return a.y < b.y;    // 按y从小到大排序  把线段的高度从低到高排序
    }
    
    void build(int k, int ll, int rr) //建树
    {
        Node[k].l = ll, Node[k].r = rr;
        Node[k].sum = Node[k].w = Node[k].lsum = 0;
        Node[k].lx = X[ll];
        Node[k].rx = X[rr];
        if(ll + 1 == rr) return;
        int m = (ll + rr) / 2;
        build(k*2, ll, m);
        build(k*2+1, m, rr);
    }
    
    
    void down(int k)  //计算长度
    {
        if(Node[k].w > 1)
        {
            Node[k].sum = Node[k].lsum = Node[k].rx - Node[k].lx;
            return;
        }
        else if(Node[k].w == 1)
        {
            Node[k].lsum = Node[k].rx - Node[k].lx;
            if(Node[k].l + 1 == Node[k].r) Node[k].sum = 0;
            else Node[k].sum = Node[k*2].lsum + Node[k*2+1].lsum;
        }
        else
        {
            if(Node[k].l + 1 == Node[k].r) Node[k].sum = Node[k].lsum = 0;
            else
            {
                Node[k].sum = Node[k*2].sum + Node[k*2+1].sum;
                Node[k].lsum = Node[k*2].lsum + Node[k*2+1].lsum;
            }
        }
    }
    
    void update(int k, edge e)  // 更新
    {
        if(Node[k].lx == e.lxx && Node[k].rx == e.rxx)
        {
            Node[k].w += e.f;
            down(k);
            return;
        }
        if(e.rxx <= Node[k*2].rx) update(k*2, e);
        else if(e.lxx >= Node[k*2+1].lx) update(k*2+1, e);
        else
        {
            edge g = e;
            g.rxx = Node[k*2].rx;
            update(k*2, g);
            g = e;
            g.lxx = Node[k*2+1].lx;
            update(k*2+1, g);
    
        }
        down(k);
    }
    int main()
    {
        int n, cnt, kase = 0, T;
        scanf("%d",&T);
        while(T--)
        {
            scanf("%d",&n);
            cnt = 0;
            for(int i=0; i<n; i++)
            {
                double x1, y1, x2, y2;
                scanf("%lf%lf%lf%lf",&x1, &y1, &x2, &y2);
                Edge[++cnt].lxx = x1, Edge[cnt].rxx = x2, Edge[cnt].y = y1, Edge[cnt].f = 1;
                X[cnt] = x1;
                Edge[++cnt].lxx = x1, Edge[cnt].rxx = x2, Edge[cnt].y = y2, Edge[cnt].f = -1;
                X[cnt] = x2;
            }
            sort(Edge+1, Edge+cnt+1, cmp);
            sort(X+1, X+cnt+1);
            int m = unique(X+1, X+cnt+1) - (X+1);
            build(1, 1, m);
            double ret = 0;
            for(int i=1; i<cnt; i++)
            {
                update(1, Edge[i]);
                ret += (Edge[i+1].y - Edge[i].y) * Node[1].sum;
            }
            printf("%.2f
    ",ret);
        }
        return 0;
    }
    自己选择的路,跪着也要走完。朋友们,虽然这个世界日益浮躁起来,只要能够为了当时纯粹的梦想和感动坚持努力下去,不管其它人怎么样,我们也能够保持自己的本色走下去。
  • 相关阅读:
    CentOS系统更换软件安装源aliyun的
    判断手机电脑微信 js
    MFC HTTP
    阿里云 镜像 源 debian
    debian root 可以远程登陆
    java-dispose方法
    深入理解JAVA序列化
    Junit单元测试--01
    算法期末考试
    矩阵连乘 动态规划
  • 原文地址:https://www.cnblogs.com/WTSRUVF/p/9274318.html
Copyright © 2020-2023  润新知