Advertisement
Guest User

Untitled

a guest
May 26th, 2016
62
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 6.11 KB | None | 0 0
  1. #include <iostream>
  2. #include <fstream>
  3. #include <algorithm>
  4. #include <vector>
  5. #include <map>
  6. #include <set>
  7. #include <memory.h>
  8. #include <cassert>
  9.  
  10. using namespace std;
  11.  
  12. const int MAXMIN = 1e9 + 1;
  13. const int MAXBOUND = 1 << 30;
  14. struct point {
  15. point() {}
  16. point(int x_, int y_ , int val_) {
  17. x = x_;
  18. y = y_;
  19. val = val_;
  20. }
  21. int x , y;
  22. int val;
  23. };
  24. struct range{
  25. range() {
  26. l = -MAXBOUND;
  27. r = +MAXBOUND;
  28. };
  29. range(int l_ , int r_) {
  30. r = r_;
  31. l = l_;
  32. }
  33. int l;
  34. int r;
  35. };
  36.  
  37. struct Node {
  38. Node(bool xdiv_): pnt(0,0,MAXMIN) {
  39. xdiv = xdiv_;
  40. mod = -1;
  41. min = MAXMIN;
  42. memset(children,0, sizeof(int) * 2);
  43. }
  44.  
  45. bool xdiv;
  46. int mod;
  47. int min;
  48. int children[2];
  49. point pnt;
  50. range dx , dy;
  51. };
  52.  
  53. bool compx(const point & a , const point & b) {
  54. if(a.x != b.x) return a.x < b.x;
  55. return a.y < b.y;
  56. }
  57.  
  58. bool compy(const point & a , const point & b) {
  59. if(a.y != b.y) return a.y < b.y;
  60. return a.x < b.x;
  61. }
  62.  
  63. long long get_dist2(const point & a , const point & b) {
  64. long long dx = a.x - b.x;
  65. long long dy = a.y - b.y;
  66. return dx * dx + dy * dy;
  67. }
  68.  
  69. range actual_range(const Node & node ,bool xdiv) {
  70. return xdiv ? node.dx : node.dy;
  71. }
  72.  
  73. int actual_crd(const point & p , bool xdiv) {
  74. return xdiv ? p.x : p.y;
  75. }
  76.  
  77. vector<point> points;
  78. int best_id;
  79.  
  80. class d2_tree {
  81. public:
  82. vector<Node> nodes;
  83. void build(vector<point> & pts) {
  84. nodes.reserve(pts.size() * 2 + 4);
  85. nodes.push_back(Node(true));
  86. int ymin = MAXBOUND;
  87. int ymax = -MAXBOUND;
  88. for(int i = 0; i < pts.size(); ++i){
  89. ymin = min(ymin , pts[i].y);
  90. ymax = max(ymax , pts[i].y);
  91. }
  92. build_node(0 , pts.begin() , pts.end() - 1 , true , range(ymin , ymax));
  93. }
  94.  
  95. void dfs(int id , int pnt_id) {
  96. const Node & cur = nodes[id];
  97. point pnt = points[pnt_id];
  98. point bestp = points[best_id];
  99. long long bestdist = get_dist2(bestp,pnt);
  100. if(cur.children[0] == 0) {
  101. if(bestdist > get_dist2(cur.pnt, pnt) || (bestdist == get_dist2(cur.pnt, pnt) && cur.pnt.val < best_id)) {
  102. if(pnt_id != cur.pnt.val) {
  103. best_id = cur.pnt.val;
  104. }
  105. }
  106. return;
  107. }
  108. Node & child1 = nodes[cur.children[0]];
  109. int k = 1;
  110.  
  111. if(actual_range(child1, cur.xdiv).r >= actual_crd(pnt, cur.xdiv)) {
  112. k = 0;
  113. }
  114.  
  115. for(int i = 0; i < 2; ++i){
  116. bestdist = get_dist2(points[best_id],pnt);
  117. int j = (i + k)%2;
  118. Node & child = nodes[cur.children[j]];
  119. range act_range = actual_range(child, cur.xdiv);
  120. long long act_crd = actual_crd(pnt, cur.xdiv);
  121. long long dist = min(abs(act_crd - act_range.r) , abs(act_crd - act_range.l));
  122. dist = min (dist , min(abs(act_crd + act_range.r) , abs(act_crd + act_range.l)));
  123. if((act_crd <= act_range.r && act_crd >= act_range.l) || dist*dist <= bestdist) {
  124. dfs(cur.children[j] , pnt_id);
  125. }
  126. }
  127. }
  128.  
  129.  
  130. private:
  131. void push(Node & cur, int val) {
  132. if(cur.children[0] == 0) return;
  133.  
  134. for(int i = 0; i < 2; ++i) {
  135. int cid = cur.children[i];
  136. nodes[cid].min = val;
  137. nodes[cid].mod = val;
  138. }
  139. }
  140.  
  141. bool check(point & pt , range & dx , range & dy) {
  142. return pt.x <= dx.r && pt.x >= dx.l && pt.y <= dy.r && pt.y >= dy.l;
  143. }
  144.  
  145. bool inside(const Node & cur ,range & dx , range & dy) {
  146. return cur.dx.r <= dx.r && cur.dx.l >= dx.l && cur.dy.r <= dy.r && cur.dy.l >= dy.l;
  147. }
  148. bool nonintersect(const Node & cur ,range & dx , range & dy) {
  149.  
  150. return cur.dx.l > dx.r || cur.dx.r < dx.l || cur.dy.l > dy.r || cur.dy.r < dy.l;
  151. }
  152.  
  153. int build_node(int id , vector<point>::iterator begin, vector<point>::iterator last, bool xdiv, range second_d) {
  154. if(last == begin) {
  155. nodes[id].dx = range(begin->x , begin->x);
  156. nodes[id].dy = range(begin->y , begin->y);
  157. nodes[id].min = begin->val;
  158. nodes[id].pnt = *begin;
  159. }
  160. else {
  161. sort(begin , last + 1 , (xdiv ? compx : compy));
  162.  
  163. if(xdiv) {
  164. nodes[id].dx = range(begin->x , last->x);
  165. nodes[id].dy = second_d;
  166. }
  167. else {
  168. nodes[id].dx = second_d;
  169. nodes[id].dy = range(begin->y , last->y);
  170. }
  171. int size = (int)(last - begin) + 1;
  172. vector<point>::iterator mid = begin + size / 2;
  173. int k = nodes.size();
  174. for(int i = 0; i < 2; ++i) {
  175. nodes[id].children[i] = k + i;
  176. nodes.push_back(!xdiv);
  177. }
  178. range next_range = (xdiv ? range(begin->x , (mid-1)->x) : range(begin->y , (mid-1)->y));
  179. nodes[id].min = min(nodes[id].min, build_node(k, begin , mid - 1, !xdiv, next_range));
  180.  
  181. next_range = (xdiv ? range((mid)->x , last->x) : range((mid)->y , last->y));
  182. nodes[id].min = min(nodes[id].min, build_node(k + 1, mid ,last , !xdiv, next_range));
  183. }
  184. return nodes[id].min;
  185. }
  186.  
  187. };
  188.  
  189. void solve() {
  190. int n;
  191. cin >> n;
  192. points.resize(n);
  193. for(int i = 0; i < n; ++i) {
  194. cin >> points[i].x >> points[i].y;
  195. points[i].val = i;
  196. }
  197.  
  198. d2_tree tree;
  199. vector<point> ptscpy = points;
  200. tree.build(ptscpy);
  201. vector<vector<int> > ans(n);
  202.  
  203. for(int i = 0; i < n; ++i) {
  204. best_id = (i == 0 ? 1 : 0);
  205. tree.dfs(0 , i);
  206. ans[best_id].push_back(i);
  207.  
  208. }
  209. for(int i = 0; i < n; ++i) {
  210. cout << i+1 <<": ";
  211. for(int j = 0; j < ans[i].size(); ++j){
  212. cout << ans[i][j] + 1 << " ";
  213. }
  214. cout << "\n";
  215. }
  216. }
  217.  
  218. int main()
  219. {
  220.  
  221. freopen("k.in","r", stdin);
  222. freopen("k.out","w", stdout);
  223.  
  224. solve();
  225. return 0;
  226. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement