391. Perfect Rectangle

问题描述:

Given N axis-aligned rectangles where N > 0, determine if they all together form an exact cover of a rectangular region.

Each rectangle is represented as a bottom-left point and a top-right point. For example, a unit square is represented as [1,1,2,2]. (coordinate of bottom-left point is (1, 1) and top-right point is (2, 2)).

Example 1:

rectangles = [
  [1,1,3,3],
  [3,1,4,2],
  [3,2,4,4],
  [1,3,2,4],
  [2,3,3,4]
]

Return true. All 5 rectangles together form an exact cover of a rectangular region.
 

Example 2:

rectangles = [
  [1,1,2,3],
  [1,3,2,4],
  [3,1,4,2],
  [3,2,4,4]
]

Return false. Because there is a gap between the two rectangular regions.
 

Example 3:

rectangles = [
  [1,1,3,3],
  [3,1,4,2],
  [1,3,2,4],
  [3,2,4,4]
]

Return false. Because there is a gap in the top center.
 

Example 4:

rectangles = [
  [1,1,3,3],
  [3,1,4,2],
  [1,3,2,4],
  [2,2,4,4]
]

Return false. Because two of the rectangles overlap with each other.
 

解题思路:

本题要求给出的矩形恰好组成一个矩形:不能有镂空,不能有重叠。要恰好组成矩形。

一开始有想是否跟 218.The Skyline Problem 相似,但是没有具体实现的头绪

看了MebiuW的解法后,利用了c++ STL自带的类型pair进行了实现

这个的解法的核心是:

  1. 利用面积来保证不会重合

  2.利用四个点来确定外边能够构成一个矩形

若所有矩形能够拼成一个完美的矩形,那么除了新矩形的四个顶点,其他的点只能出现偶数次,最多4次。

我用set来辅助我进行这个操作:set中含有就erase该元素,set中不含有就加入这个元素

这是一个充分条件但不是一个必要条件。

所以我们也需要检查:最后剩余的四个点是否就是四个顶点。

代码:

class Solution {
public:
    bool isRectangleCover(vector<vector<int>>& rectangles) {
        if(rectangles.empty() || rectangles[0].empty())
            return false;
        set<pair<int, int>> s;
        int area = 0;
        pair<int,int> b_l(INT_MAX, INT_MAX);
        pair<int,int> t_r(INT_MIN, INT_MIN);
        for(int i = 0; i < rectangles.size(); i++){
            pair<int, int> cur_bl(rectangles[i][0], rectangles[i][1]);
            pair<int, int> cur_tr(rectangles[i][2], rectangles[i][3]);
            if(cur_bl < b_l){
                b_l.first = cur_bl.first;
                b_l.second = cur_bl.second;
            }
            if(cur_tr > t_r){
                t_r.first = cur_tr.first;
                t_r.second = cur_tr.second;
            }
            pair<int, int> cur_tl(rectangles[i][0],rectangles[i][3]);
            pair<int, int> cur_br(rectangles[i][2],rectangles[i][1]);
            
            if(s.count(cur_bl)){
                s.erase(cur_bl);
            }else{
                s.insert(cur_bl);
            }
            if(s.count(cur_tr)){
                s.erase(cur_tr);
            }else{
                s.insert(cur_tr);
            }
            if(s.count(cur_tl)){
                s.erase(cur_tl);
            }else{
                s.insert(cur_tl);
            }
            if(s.count(cur_br)){
                s.erase(cur_br);
            }else{
                s.insert(cur_br);
            }
            area += ((cur_tr.first - cur_bl.first)*(cur_tr.second - cur_bl.second));
        }
        int total_area = (t_r.first - b_l.first)*(t_r.second - b_l.second);
        if(s.size() != 4 || area != total_area)
            return false;
        pair<int,int> b_r(t_r.first, b_l.second);
        pair<int,int> t_l(b_l.first, t_r.second);
        if(!s.count(b_r) || !s.count(b_l) || !s.count(t_r) || !s.count(t_l))
            return false;
        return true;
    }
};
原文地址:https://www.cnblogs.com/yaoyudadudu/p/9167286.html