CF97B Superset
阿新 • • 發佈:2018-11-28
sdi con pro 條件 嘟嘟 存在 ans 問題 stream
嘟嘟嘟cf
嘟嘟嘟luogu
剛開始我看成了對於一個點\(i\),存在一個點\(j\)滿足三個條件之一,而不是任意的\(j\)。結果自然\(gg\)了,第二個點就\(WA\)了。
也不知怎麽來的思路:平面分治。
先把所有點按\(x\)排序,然後規定一個中間點\(a_{mid}\)。兩邊的點向中間點作投影,這樣對於任意的在左半部分的點\(i\)和任意的在右半部分的點\(j\),必定滿足條件。
然後我們在分治到\([L, mid - 1]\)和\([mid + 1, R]\)中,解決同側點的問題。
#include<cstdio> #include<iostream> #include<cmath> #include<algorithm> #include<cstring> #include<cstdlib> #include<cctype> #include<vector> #include<stack> #include<queue> #include<map> using namespace std; #define enter puts("") #define space putchar(‘ ‘) #define Mem(a, x) memset(a, x, sizeof(a)) #define rg register typedef long long ll; typedef double db; const int INF = 0x3f3f3f3f; const db eps = 1e-8; const int maxn = 2e5 + 5; inline ll read() { ll ans = 0; char ch = getchar(), last = ‘ ‘; while(!isdigit(ch)) last = ch, ch = getchar(); while(isdigit(ch)) ans = (ans << 1) + (ans << 3) + ch - ‘0‘, ch = getchar(); if(last == ‘-‘) ans = -ans; return ans; } inline void write(ll x) { if(x < 0) x = -x, putchar(‘-‘); if(x >= 10) write(x / 10); putchar(x % 10 + ‘0‘); } int n, cnt; struct Node { int x, y; bool operator < (const Node& oth)const { return x < oth.x || (x == oth.x && y < oth.y); } bool operator == (const Node& oth)const { return x == oth.x && y == oth.y; } }a[maxn]; void solve(int L, int R) { if(L > R) return; int mid = (L + R) >> 1; for(int i = L; i <= R; ++i) a[++n] = (Node){a[mid].x, a[i].y}; solve(L, mid - 1); solve(mid + 1, R); } int main() { n = read(); for(int i = 1; i <= n; ++i) a[i].x = read(), a[i].y = read(); sort(a + 1, a + n + 1); solve(1, n); sort(a + 1, a + n + 1); int _n = unique(a + 1, a + n + 1) - a - 1; write(_n), enter; for(int i = 1; i <= _n; ++i) write(a[i].x), space, write(a[i].y), enter; return 0; }
CF97B Superset