#include <algorithm> #include <list> #include <vector> #include <cassert> #include <iostream> #include <sstream> using namespace std; struct Rectangle { Rectangle() { } Rectangle(int x1, int y1, int x2, int y2) : x1_(x1), y1_(y1), x2_(x2), y2_(y2) { } bool operator & (const Rectangle & r) const { return max(x1_, r.x1_) < min(x2_, r.x2_) and max(y1_, r.y1_) < min(y2_, r.y2_); } bool contains(const Rectangle & r) const { return x1_ <= r.x1_ and x2_ >= r.x2_ and y1_ <= r.y1_ and y2_ >= r.y2_; } Rectangle & operator &= (const Rectangle & r) { x1_ = min(x1_, r.x1_); y1_ = min(y1_, r.y1_); x2_ = max(x2_, r.x2_); y2_ = max(y2_, r.y2_); return *this; } bool operator < (const Rectangle r) const { if (x1_ != r.x1_) return x1_ < r.x1_; if (x2_ != r.x2_) return x2_ < r.x2_; if (y1_ != r.y1_) return y1_ < r.y1_; return y2_ < r.y2_; } friend ostream & operator << (ostream & os, const Rectangle &r) { os << r.x1_ << ' ' << r.x2_ << ' ' << r.y1_ << ' ' << r.y2_; return os; } friend istream & operator >> (istream & is, Rectangle & r) { is >> r.x1_ >> r.x2_ >> r.y1_ >> r.y2_; return is; } private: int x1_, y1_, x2_, y2_; }; int main() { int n; cin >> n; list<Rectangle> rectangles; typedef list<Rectangle>::iterator RecIter; vector<Rectangle> rectangles2; rectangles2.reserve(n); for (int i = 0 ; i < n ; i++) { Rectangle current; cin >> current; rectangles2.push_back(current); } random_shuffle(rectangles2.begin(), rectangles2.end()); for (int i = 0 ; i < n ; i++) { Rectangle current = rectangles2[i]; bool cont = true; bool eaten = false; while(cont) { cont = false; for (RecIter it = rectangles.begin(); it != rectangles.end();) { if (current.contains(*it)) { it = rectangles.erase(it); } else if(it->contains(current)) { assert(cont == false); eaten = true; break; } else if (*it & current) { cont = true; current &= *it; it = rectangles.erase(it); } else ++it; } } if (!eaten) rectangles.push_back(current); } rectangles.sort(); cout << rectangles.size() << '\n'; for (RecIter it = rectangles.begin(); it != rectangles.end(); ++it) std::cout << *it << '\n'; }
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 | #include <algorithm> #include <list> #include <vector> #include <cassert> #include <iostream> #include <sstream> using namespace std; struct Rectangle { Rectangle() { } Rectangle(int x1, int y1, int x2, int y2) : x1_(x1), y1_(y1), x2_(x2), y2_(y2) { } bool operator & (const Rectangle & r) const { return max(x1_, r.x1_) < min(x2_, r.x2_) and max(y1_, r.y1_) < min(y2_, r.y2_); } bool contains(const Rectangle & r) const { return x1_ <= r.x1_ and x2_ >= r.x2_ and y1_ <= r.y1_ and y2_ >= r.y2_; } Rectangle & operator &= (const Rectangle & r) { x1_ = min(x1_, r.x1_); y1_ = min(y1_, r.y1_); x2_ = max(x2_, r.x2_); y2_ = max(y2_, r.y2_); return *this; } bool operator < (const Rectangle r) const { if (x1_ != r.x1_) return x1_ < r.x1_; if (x2_ != r.x2_) return x2_ < r.x2_; if (y1_ != r.y1_) return y1_ < r.y1_; return y2_ < r.y2_; } friend ostream & operator << (ostream & os, const Rectangle &r) { os << r.x1_ << ' ' << r.x2_ << ' ' << r.y1_ << ' ' << r.y2_; return os; } friend istream & operator >> (istream & is, Rectangle & r) { is >> r.x1_ >> r.x2_ >> r.y1_ >> r.y2_; return is; } private: int x1_, y1_, x2_, y2_; }; int main() { int n; cin >> n; list<Rectangle> rectangles; typedef list<Rectangle>::iterator RecIter; vector<Rectangle> rectangles2; rectangles2.reserve(n); for (int i = 0 ; i < n ; i++) { Rectangle current; cin >> current; rectangles2.push_back(current); } random_shuffle(rectangles2.begin(), rectangles2.end()); for (int i = 0 ; i < n ; i++) { Rectangle current = rectangles2[i]; bool cont = true; bool eaten = false; while(cont) { cont = false; for (RecIter it = rectangles.begin(); it != rectangles.end();) { if (current.contains(*it)) { it = rectangles.erase(it); } else if(it->contains(current)) { assert(cont == false); eaten = true; break; } else if (*it & current) { cont = true; current &= *it; it = rectangles.erase(it); } else ++it; } } if (!eaten) rectangles.push_back(current); } rectangles.sort(); cout << rectangles.size() << '\n'; for (RecIter it = rectangles.begin(); it != rectangles.end(); ++it) std::cout << *it << '\n'; } |