• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            隨筆 - 97, 文章 - 22, 評論 - 81, 引用 - 0
            數據加載中……

            HDU 3373 Point

            題目鏈接:http://acm.hdu.edu.cn/showproblem.php?pid=3706
            /*
            題意:
                給定N(N <= 100000)個點,要求找到任意一個點的最近點,點的距離定義如下:
            Distance (A, B) = max (|Ax – Bx|, |Ay – By|),求出所有點的Distance和。

            解法:
            二維線段樹

            思路:
                我的做法是利用二維線段樹的二維區間求和,首先數字太大,需要離散化,然后
            將所有數字插入到離散后的二維線段樹區間,二維線段樹維護一個Sum域,表示該二維
            區間插入過的數字總和,然后對于每個點,二分枚舉和它最近的點的距離,根據這個
            距離找到最大的被這個距離包含的并且在二維線段樹管轄范圍的二維區間,查詢那段
            區間的Sum值,如果Sum值大于1的話說明這個范圍不止一個點,于是可以縮小枚舉的范
            圍,直到找到最小的枚舉值,就是這個點的最近點,總的復雜度O(nlog(n)log(n))。
                這里需要注意的是,二維區間的Sum和統計和插入點的時候處理不好可能會在同一
            區間插入多次或者統計多次,這和區間最值有所不同,需要特殊處理二維區間的某一維
            的長度為1的情況。
            */

            #include 
            <iostream>
            #include 
            <cmath>
            #include 
            <algorithm>
            using namespace std;

            #define maxn 200010
            #define eps 1e-6
            #define maxaxis 1000000000
            #define ll __int64
            typedef 
            int Type;


            Type bin[maxn];
            int size, tot;

            int B(Type val) {
                
            int l = 0;
                
            int r = tot-1;
                
            while(l <= r) {
                    
            int m = (l + r) >> 1;
                    
            if(bin[m] == val)
                        
            return m;
                    
            if(val > bin[m]) {
                        l 
            = m + 1;
                    }
            else
                        r 
            = m - 1;
                }

            }


            struct point {
                
            int x, y;
                
            int _ix, _iy;
            }
            P[maxn];

            struct Tree {
                
            int son[4];
                Type Sum;

                
            void clear() {
                    Sum 
            = 0;
                    
            for(int i = 0; i < 4; i++)
                        son[i] 
            = -1;
                }

            }
            T[maxn*6];
            int root, all;

            void Insert(int& root, int x, int y, int lx, int rx, int ly, int ry) {
                
            if(x > rx || x < lx || y > ry || y < ly)
                    
            return ;

                
            if(root == -1{
                    root 
            = all++;
                    T[root].clear();
                }


                
            if(lx == rx && x == lx && y == ly && ly == ry) {
                    T[root].Sum 
            ++;
                    
            return ;
                }


                
            int midx0 = (lx + rx) >> 1;
                
            int midy0 = (ly + ry) >> 1;
                
            int midx1 = (lx==rx) ? midx0 : midx0 + 1;
                
            int midy1 = (ly==ry) ? midy0 : midy0 + 1;

                
            if(lx == rx) {
                    Insert(T[root].son[
            0], x, y, lx, midx0, ly, midy0);
                    Insert(T[root].son[
            1], x, y, lx, midx0, midy1, ry);
                }
            else if(ly == ry) {
                    Insert(T[root].son[
            1], x, y, lx, midx0, midy1, ry);
                    Insert(T[root].son[
            2], x, y, midx1, rx, ly, midy0);
                }
            else {
                    Insert(T[root].son[
            0], x, y, lx, midx0, ly, midy0);
                    Insert(T[root].son[
            1], x, y, lx, midx0, midy1, ry);
                    Insert(T[root].son[
            2], x, y, midx1, rx, ly, midy0);
                    Insert(T[root].son[
            3], x, y, midx1, rx, midy1, ry);
                }



                
            int i;
                T[root].Sum 
            = 0;
                
            for(i = 0; i < 4; i++{
                    
            if(T[root].son[i] != -1{
                        T[root].Sum 
            += T[ T[root].son[i] ].Sum;
                    }

                }

            }


            void Query(int root, int x0, int x1, int y0, int y1, 
                                  
            int lx, int rx, int ly, int ry, Type& Num) {
                
            if(x0 > rx || x1 < lx || y0 > ry || y1 < ly || root == -1)
                    
            return ;

                
            if(Num > 1)
                    
            return ;

                
            if(x0 <= lx && rx <= x1 && y0 <= ly && ry <= y1) {
                    Num 
            += T[root].Sum;
                    
            return ;
                }


                
            int midx0 = (lx + rx) >> 1;
                
            int midy0 = (ly + ry) >> 1;
                
            int midx1 = (lx==rx) ? midx0 : midx0 + 1;
                
            int midy1 = (ly==ry) ? midy0 : midy0 + 1;
                
                
            if(lx == rx) {
                    Query(T[root].son[
            0], x0, x1, y0, y1, lx, midx0, ly, midy0, Num);
                    Query(T[root].son[
            1], x0, x1, y0, y1, lx, midx0, midy1, ry, Num);
                }
            else if(ly == ry) {
                    Query(T[root].son[
            1], x0, x1, y0, y1, lx, midx0, midy1, ry, Num);
                    Query(T[root].son[
            2], x0, x1, y0, y1, midx1, rx, ly, midy0, Num);
                }
            else {
                    Query(T[root].son[
            0], x0, x1, y0, y1, lx, midx0, ly, midy0, Num);
                    Query(T[root].son[
            1], x0, x1, y0, y1, lx, midx0, midy1, ry, Num);
                    Query(T[root].son[
            2], x0, x1, y0, y1, midx1, rx, ly, midy0, Num);
                    Query(T[root].son[
            3], x0, x1, y0, y1, midx1, rx, midy1, ry, Num);
                }

            }


            int LargeThan(int val, int pre) {
                
            int l = 0;
                
            int r = pre;
                
            int ans = l;
                
            while(l <= r) {
                    
            int m = (l + r) >> 1;
                    
            if(val <= bin[m]) {
                        r 
            = m - 1;
                        ans 
            = m;
                    }
            else
                        l 
            = m + 1;
                }

                
            return ans;
            }


            int LessThan(int val, int pre) {
                
            int l = pre;
                
            int r = tot - 1;
                
            int ans = r;
                
            while(l <= r) {
                    
            int m = (l + r) >> 1;
                    
            if(val >= bin[m]) {
                        l 
            = m + 1;
                        ans 
            = m;
                    }
            else
                        r 
            = m - 1;
                }

                
            return ans;
            }


            int Process(int idx, int dis) {
                
            int xleft  = LargeThan( P[idx].x - dis, P[idx]._ix );
                
            int yleft  = LargeThan( P[idx].y - dis, P[idx]._iy );
                
            int xright =  LessThan( P[idx].x + dis, P[idx]._ix );
                
            int yright =  LessThan( P[idx].y + dis, P[idx]._iy );
                
            int Num = 0;
                Query(root, xleft, xright, yleft, yright, 
            0, tot-10, tot-1, Num);
                
            return Num;
            }


            int n;
            int main() {
                
            int i;
                
            int Max;

                
            while(scanf("%d"&n) != EOF) {
                    size 
            = 0;
                    tot 
            = 0;
                    all 
            = 0;
                    Max 
            = 0;
                    
            for(i = 0; i < n; i++{
                        scanf(
            "%d %d"&P[i].x, &P[i].y);
                        bin[ size
            ++ ] = P[i].x;
                        bin[ size
            ++ ] = P[i].y;
                        
            if(P[i].x > Max) Max = P[i].x;
                        
            if(P[i].y > Max) Max = P[i].y;
                    }

                    sort(bin, bin 
            + size);
                    
            for(i = 0; i < size; i++{
                        
            if(i == 0 || bin[i] != bin[i-1])
                            bin[tot
            ++= bin[i];
                    }

                    root 
            = -1;
                    
            for(i = 0; i < n; i++{
                        P[i]._ix 
            = B(P[i].x);
                        P[i]._iy 
            = B(P[i].y);
                        Insert(root, P[i]._ix, P[i]._iy, 
            0, tot-10, tot-1);
                    }


                    ll ans 
            = 0;
                    
            for(i = 0; i < n; i++{
                        
            int l = 0;
                        
            int r = Max;
                        
            int dis = 0;
                        
            while(l <= r) {
                            
            int m = (l + r) >> 1;
                            
            if(Process(i, m) > 1{
                                r 
            = m - 1;
                                dis 
            = m;
                            }
            else
                                l 
            = m + 1;
                        }

                        ans 
            += dis;
                    }

                    printf(
            "%I64d\n", ans);
                }

                
            return 0;
            }


            posted on 2011-04-04 21:54 英雄哪里出來 閱讀(1381) 評論(0)  編輯 收藏 引用 所屬分類: 線段樹

            国产亚洲欧美成人久久片| 久久青青草原精品国产不卡| 国产精品热久久毛片| 久久人人爽人人爽人人片AV不 | 久久久久亚洲av无码专区导航| 久久亚洲国产成人精品无码区| 国产精品激情综合久久| 久久99国产精品久久99果冻传媒| 久久天天躁狠狠躁夜夜avapp| 久久久久人妻一区精品色 | 狠狠色狠狠色综合久久| 波多野结衣久久精品| 国内精品久久久久影院老司| 一本一本久久a久久精品综合麻豆| 亚洲国产精品一区二区三区久久 | 久久精品亚洲男人的天堂| 国产一区二区三精品久久久无广告| 26uuu久久五月天| 久久一区二区免费播放| 99久久免费国产精品特黄| 久久夜色精品国产噜噜噜亚洲AV | 精品久久久久久无码中文字幕 | 91精品国产综合久久香蕉| 色综合久久综合网观看| 日韩十八禁一区二区久久| 久久亚洲精品无码aⅴ大香| 国产成人久久精品激情 | 精品午夜久久福利大片| 国产真实乱对白精彩久久| 亚洲精品99久久久久中文字幕| 97精品依人久久久大香线蕉97| 国产精品免费福利久久| 久久se这里只有精品| 亚洲午夜久久久久妓女影院 | 精品久久人人做人人爽综合| 一本色道久久88综合日韩精品 | 99久久久久| 亚洲国产精品久久久天堂| 国产午夜电影久久| 久久综合亚洲色HEZYO社区| 国产成人精品久久亚洲|