zoukankan      html  css  js  c++  java
  • 暑假集训-数据结构

    求矩形的并 Poj1151

    线段树,离散化,扫描线。

      1 #include <iostream>
      2 #include <cstdio>
      3 #include <fstream>
      4 #include <algorithm>
      5 #include <cmath>
      6 #include <deque>
      7 #include <vector>
      8 #include <queue>
      9 #include <string>
     10 #include <cstring>
     11 #include <map>
     12 #include <stack>
     13 #include <set>
     14 #define LL long long
     15 #define INF 0x3f3f3f3f
     16 #define OPEN_FILE
     17 using namespace std;
     18 const int MAXN = 5005;
     19 struct Line{
     20     double left, right;
     21     double y;
     22     int cnt;
     23     Line(){};
     24     Line(double left, double right, double y, int cnt) :left(left), right(right), y(y), cnt(cnt){};
     25 };
     26 bool operator < (Line a, Line b){
     27     return a.y < b.y;
     28 }
     29 struct Node{
     30     double left, right;
     31     int from, to;
     32     int cnt;
     33     double value;
     34 };
     35 int n;
     36 double a[MAXN];
     37 Line scan[MAXN];
     38 Node f[MAXN << 1];
     39 void build(int t, int left, int right){
     40     f[t].left = a[left];
     41     f[t].right = a[right];
     42     f[t].from = left;
     43     f[t].to = right;
     44     f[t].cnt = f[t].value = 0;
     45     if (right - left == 1) return;
     46     int mid = (left + right) >> 1;
     47     build(t << 1, left, mid);
     48     build((t << 1) + 1, mid, right);
     49 }
     50 void update(int t, Line p){
     51     if (p.left == f[t].left && p.right == f[t].right){
     52         f[t].cnt += p.cnt;
     53         if (f[t].cnt > 0){
     54             f[t].value = p.right - p.left;
     55             return;
     56         }
     57         if (f[t].to - f[t].from == 1){
     58             f[t].value = 0;
     59         }
     60         else{
     61             f[t].value = f[t << 1].value + f[(t << 1) + 1].value;
     62         }
     63         return;
     64     }
     65     if (p.left >= f[(t << 1) + 1].left){
     66         update((t << 1) + 1, p);
     67     }
     68     else if (p.right <= f[t << 1].right){
     69         update(t << 1, p);
     70     }
     71     else{
     72         Line q = p;
     73         q.right = f[t << 1].right;
     74         update(t << 1, q);
     75         q = p;
     76         q.left = f[(t << 1) + 1].left;
     77         update((t << 1) + 1, q);
     78     }
     79     if (f[t].cnt > 0){
     80         f[t].value = f[t].right - f[t].left;
     81     }
     82     else{
     83         f[t].value = f[t].to - f[t].from == 1 ?0:f[t << 1].value + f[(t << 1) + 1].value;
     84     }
     85 }
     86 int main()
     87 {
     88 #ifdef OPEN_FILE
     89     //freopen("in.txt", "r", stdin);
     90     //freopen("out.txt", "w", stdout);
     91 #endif // OPEN_FILE
     92     double x1, y1, x2, y2;
     93     int cas = 1;
     94     while (~scanf("%d", &n) && n != 0){
     95         for (int i = 1; i <= n; i++){
     96             scanf("%lf%lf%lf%lf", &x1, &y1, &x2, &y2);
     97             a[i * 2 - 1] = x1;
     98             a[i * 2] = x2;
     99             scan[i * 2 - 1] = Line(x1, x2, y1, 1);
    100             scan[i * 2] = Line(x1, x2, y2, -1);
    101         }
    102         n = n * 2;
    103         double ans = 0.0;
    104         memset(f, 0, sizeof(f));
    105         sort(a + 1, a + n + 1);
    106         sort(scan + 1, scan + n + 1);
    107         build(1, 1, n);
    108         update(1, scan[1]);
    109         for (int i = 2; i <= n; i++){
    110             ans += f[1].value * (scan[i].y - scan[i - 1].y);
    111             update(1, scan[i]);
    112         }
    113         printf("Test case #%d
    Total explored area: %.2lf
    
    ", cas++, ans);
    114     }
    115 }
    View Code

    并查集应用 poj1182

    以前对并查集的印象还停留在高中,只是记录一下是不是已经连通。这里加了一个数组rank[i]表示i的秩,也就是到祖先的距离,其实都是高中的内容。

    //set
    void MakeSet(int x){
        father[x] = x;
        rank[x] = 0;
    }
    //find
    int FindSet(int x)
    {
        if (x != father[x])
        {
            father[x] = FindSet(father[x]);
        }
        return father[x];
    }
    //union
    void Union(int x, int y)
    {
        x = FindSet(x);
        y = FindSet(y);
        if (x == y) return;
        if (rank[x] > rank[y])
        {
            father[y] = x;
            rank[x] += rank[y];
        }
        else
        {
            if (rank[x] == rank[y])
            {
                rank[y]++;
            }
            father[x] = y;
        }
    }
  • 相关阅读:
    Android应用开发笔记——打造自己的标签栏
    ZeroMQ 的模式[转]
    安装python/wingware
    新手该如何学python怎么学好python?
    membase 简介
    前端学习网站推荐
    签了工作之后才发现,自己太草率了.....我看过的关于职业规划最好最全面的一篇文章[转]
    Nagio监控系统介绍
    thread_union位置
    音频采样位数问题
  • 原文地址:https://www.cnblogs.com/macinchang/p/4661697.html
Copyright © 2011-2022 走看看