码迷,mamicode.com
首页 > 其他好文 > 详细

LeetCode 面试题 16.03. 交点

时间:2020-04-12 22:28:11      阅读:77      评论:0      收藏:0      [点我收藏+]

标签:误差   art   多个   end   表示   back   cto   inter   浮点运算   

题目描述:

给定两条线段(表示为起点start = {X1, Y1}和终点end = {X2, Y2}),如果它们有交点,请计算其交点,没有交点则返回空值。

要求浮点型误差不超过10^-6。若有多个交点(线段重叠)则返回 X 值最小的点,X 坐标相同则返回 Y 值最小的点。

 

就是要分类讨论一下,要注意的是在判断两条线段是否相交时,不要使用浮点运算,可能会造成判断错误。

class Solution {
public:
    vector<double> intersection(vector<int>& start1, vector<int>& end1, vector<int>& start2, vector<int>& end2) {
        //设置别称,方便写代码
        const int& x1 = start1[0];
        const int& y1 = start1[1];
        const int& x2 = end1[0];
        const int& y2 = end1[1];
        const int& x3 = start2[0];
        const int& y3 = start2[1];
        const int& x4 = end2[0];
        const int& y4 = end2[1];

        //计算两条直线的系数
        int A1, B1, C1, A2, B2, C2;
        A1 = y1 - y2;
        B1 = x2 - x1;
        C1 = y2 * x1 - y1 * x2;
        A2 = y3 - y4;
        B2 = x4 - x3;
        C2 = y4 * x3 - y3 * x4;

        vector<double> res;
        if ((y2-y1)*(x4-x3) != (x2-x1)*(y4-y3)) {//如果斜率不同,这种情况不可能重合
            //测试是否相交
            if (A1 * x3 + B1 * y3 + C1 == 0) { res.push_back(x3); res.push_back(y3); return res;}
            if (A1 * x4 + B1 * y4 + C1 == 0) { res.push_back(x4); res.push_back(y4); return res;}
            if (A2 * x1 + B2 * y1 + C2 == 0) { res.push_back(x1); res.push_back(y1); return res;}
            if (A2 * x2 + B2 * y2 + C2 == 0) { res.push_back(x2); res.push_back(y2); return res;}

            if ((A1 * x3 + B1 * y3 + C1) * (A1 * x4 + B1 * y4 + C1) < 0
                && (A2 * x1 + B2 * y1 + C2) * (A2 * x2 + B2 * y2 + C2) < 0) {
                res.push_back(B2*C1 - B1*C2);
                res.push_back(A1*C2 - A2*C1);
                res[0] /= A2 * B1 - A1 * B2;
                res[1] /= A2 * B1 - A1 * B2;
                return res;
            }
            else return res;
        }
        else {//斜率相同,这种时候有可能重合,也有可能平行
            if (A1 * x3 + B1 * y3 + C1 == 0) {//两条直线是重合的
                if (x1 != x2){//不垂直y轴
                    if (max(x1, x2) >= min(x3, x4) && min(x3,x4) >= min(x1,x2)) {
                        if (x3 < x4) return vector<double> {double(x3), double(y3)};
                        else return vector<double> {double(x4), double(y4)};
                    }
                    else if (max(x3, x4) >= min(x1, x2) && min(x3, x4) <= min(x1, x2)) {
                        if (x1 < x2) return vector<double> {double(x1), double(y1)};
                        else return vector<double> {double(x2), double(y2)};
                    }
                    else {
                        return res;
                    }
                }
                else {//垂直y轴
                    if (max(y1, y2) >= min(y3, y4) && min(y3, y4) >= min(y1, y2)) {
                        if (y3 < y4) return vector<double> {double(x3), double(y3)};
                        else return vector<double> {double(x4), double(y4)};
                    }
                    else if (max(y3, y4) >= min(y1, y2) && min(y3, y4) <= min(y1, y2)) {
                        if (y1 < y2) return vector<double> {double(x1), double(y1)};
                        else return vector<double> {double(x2), double(y2)};
                    }
                    else {
                        return res;
                    }
                }
                
            }
            else {//平行
                return res;
            }
        }
    }
};

技术图片

LeetCode 面试题 16.03. 交点

标签:误差   art   多个   end   表示   back   cto   inter   浮点运算   

原文地址:https://www.cnblogs.com/airfy/p/12687934.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!