LeetCode 356. Line Reflection

Given n points on a 2D plane, find if there is such a line parallel to y-axis that reflect the given set of points.

Example 1:
Given points = [[1,1],[-1,1]], return true.

Example 2:
Given points = [[1,1],[-1,-1]], return false.

Follow up:
Could you do better than O(n2)?

Hint:

Find the smallest and largest x-value for all points.
If there is a line then it should be at y = (minX + maxX) / 2.
For each point, make sure that it has a reflected point in the opposite side.

s思路:
1. 根据hint,先确定对称线的位置。
2. 先看简单粗暴的没脑子的做法:n个点每一对点组成的线段都测试一次看是否和对称线垂直,复杂度就是o(n^2)。如何简化呢?仔细观察,上面的做法每一个点都要和其他n-1个点实验,而最终只有一个点组成线段满足条件,甚至没有一个点,大部分的运算是无效的。这样的问题,我们其实很熟悉。换一个思路,我们可以根据每个点和对称线,先计算对称点应该的坐标,然后查询即可。这样只需要n次计算坐标和n次查询。
3. 要考虑的edge case,比如:刚好有点就落在对称线上,那么就不用管,自己和自己对称;有多个点的坐标相等,这也需要对称点的坐标重合

//方法1:把所有点存在unordered_map<int,set<int>> mm
bool isReflected(vector<pair<int, int>>& points) {
    //
    unordered_map<int,set<int>> mm;
    int minx=INT_MAX,maxx=INT_MIN;
    for(auto point:points){
        minx=min(minx,point.first);
        maxx=max(maxx,point.first);         
        mm[point.first].insert(point.second);
    }
    long yy=long(minx)+long(maxx);
    for(auto point:points){
        int reflect=yy-point.first;
        if(mm.count(reflect)==0||mm[reflect].count(point.second)==0) return false;  
    }
    return true;
}
//方法2:把所有点直接存unordered_set<pair<int,int>>内,由于hash function对pair没有定义,需要自己定义,因此要麻烦很多!!但是速度快啊!参考https://discuss.leetcode.com/topic/48173/o-n-time-space-complexity-c-solution-with-unordered_set

struct hashpair{
    template<typename T, typename U>
    std::size_t operator()(const std::pair<T,U>&x) const
    {
        return (std::hash<T>()(x.first)<<1)^(std::hash<U>()(x.second));
    }
};

//如果不考虑template,可以直接写成,

struct hashpair{
    std::size_t operator()(const std::pair<int,int>&x) const
    {
        return  (std::hash<int>()(x.first)<<1)^(std::hash<int>()(x.second));
    }
};


bool isReflected(vector<pair<int, int>>& points) {
    //
    unordered_set<pair<int,int>,hashpair> ss;
    int minx=INT_MAX,maxx=INT_MIN;
    for(auto point:points){
        minx=min(minx,point.first);
        maxx=max(maxx,point.first);     
        ss.insert(point);   
    }
    long yy=long(minx)+long(maxx);
    for(auto point:points){
        int reflect=yy-point.first;
        if(ss.count({reflect,point.second})==0) return false;   
    }
    return true;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值