【34】C++实战篇—— 已知pt1,pt2代表一条直线(已知直线上两点),给定x1,x2 求pts1,pts2,给定y1,y2 求pts1,pts2;线段方程求坐标;方向向量求坐标;斜率求坐标

1 给定x1,x2 求pts1,pts2

已知直线上2个点坐标cv::Point2f pt1,pt2,如果输入 y1 和 y2 ,求 y1 和 y2对应的两个坐标点存入cv::Point2f pts1,pts2;

1.1 使用斜率计算坐标

需考虑斜率存在和不存在情况
分析:

  1. 如果斜率存在则根据斜率计算出对应坐标;
    2.当斜率不存在或者很大的时候,考虑是垂直直线,那么竖线的pts1.y = pt1.y,pts2.y=pt2.y;
#include <opencv2/opencv.hpp>

using namespace cv;

void getPointsOnLine(Point2f pt1, Point2f pt2, float y1, float y2, Point2f& pts1, Point2f& pts2) {
    float k = (pt2.x - pt1.x) == 0 ? std::numeric_limits<float>::max() : (pt2.y - pt1.y) / (pt2.x - pt1.x); // 计算直线的斜率,如果直线垂直于 x 轴,则斜率为无穷大

    if (std::abs(k) > 1000) { // 如果斜率不存在或者很大(近似垂直)
        // 直接使用给定的 x 坐标
        pts1.x = pt1.x;
        pts2.x = pt2.x;
    } else {
        // 根据斜率计算对应的 x 坐标
        float b = pt1.y - k * pt1.x; // 计算直线的截距
        pts1.x = (y1 - b) / k;
        pts2.x = (y2 - b) / k;
    }

    // 将给定的 y 坐标存入 pts1 和 pts2 中
    pts1.y = y1;
    pts2.y = y2;
}

int main() {
    // 已知直线上的两个点坐标
    Point2f pt1(10, 20);
    Point2f pt2(50, 80);

    // 输入的 y1 和 y2 值
    float y1 = 30;
    float y2 = 90;

    // 得到 y1 和 y2 对应的两个坐标点
    Point2f pts1, pts2;
    getPointsOnLine(pt1, pt2, y1, y2, pts1, pts2);

    // 输出结果
    std::cout << "Point 1 on line: (" << pts1.x << ", " << pts1.y << ")" << std::endl;
    std::cout << "Point 2 on line: (" << pts2.x << ", " << pts2.y << ")" << std::endl;

    return 0;
}

1.2 线段方程来计算 —— 不使用斜率

如果不使用斜率的方法,我们可以考虑直接通过线段方程来计算。线段方程可以通过直线两点来表示。

假设直线上两个点的坐标为 pt1 和 pt2,我们可以使用线段方程来计算 y1 和 y2 对应的两个坐标点。线段方程的一般形式为:

在这里插入图片描述

//已知直线上2点pt1,pt2,输入 y1 和 y2 ,求对应的两个坐标点存入pts1,pts2
void getLine::getPointsOnLineV(cv::Point2f pt1, cv::Point2f pt2, float y1, float y2, cv::Point2f& pts1, cv::Point2f& pts2)
{
	// 计算参数 t
	float t1 = (y1 - pt1.y) / (pt2.y - pt1.y);
	float t2 = (y2 - pt1.y) / (pt2.y - pt1.y);

	// 计算对应的两个坐标点
	pts1 = pt1 + t1 * (pt2 - pt1);
	pts2 = pt1 + t2 * (pt2 - pt1);
}

1.3 方向向量线来计算 —— 不使用斜率

果不使用斜率的方法,我们可以通过直接计算线段的方向向量,并根据给定的 y1 和 y2 值来计算对应的两个坐标点。具体步骤如下:

  • 1.计算直线上两个点 pt1 和 pt2 的方向向量 vec,即 vec = pt2 - pt1
  • 2.计算 pt1 和 pt2 之间的长度 length,即 length = norm(vec)
  • 3.根据给定的 y1 和 y2 值,计算参数 t1 和 t2,其中 t1 = (y1 - pt1.y) / vec.y 和 t2 = (y2 - pt1.y) / vec.y
  • 4.计算对应的两个坐标点 pts1 和 pts2,其中 pts1 = pt1 + t1 * vec 和 pts2 = pt1 + t2 * vec
#include <opencv2/opencv.hpp>

using namespace cv;
using namespace std;

void getPointsOnLine(Point2f pt1, Point2f pt2, float y1, float y2, Point2f& pts1, Point2f& pts2) {
    // 计算直线上的方向向量
    Point2f vec = pt2 - pt1;

    // 计算直线的长度
    float length = norm(vec);

    // 计算参数 t
    float t1 = (y1 - pt1.y) / vec.y;
    float t2 = (y2 - pt1.y) / vec.y;

    // 计算对应的两个坐标点
    pts1 = pt1 + t1 * vec;
    pts2 = pt1 + t2 * vec;
}

int main() {
    // 已知直线上的两个点坐标
    Point2f pt1(10, 20);
    Point2f pt2(50, 80);

    // 输入的 y1 和 y2 值
    float y1 = 30;
    float y2 = 90;

    // 得到 y1 和 y2 对应的两个坐标点
    Point2f pts1, pts2;
    getPointsOnLine(pt1, pt2, y1, y2, pts1, pts2);

    // 输出结果
    cout << "Point 1 on line: (" << pts1.x << ", " << pts1.y << ")" << endl;
    cout << "Point 2 on line: (" << pts2.x << ", " << pts2.y << ")" << endl;

    return 0;
}

2 给定y1,y2 求pts1,pts2

2.2 线段方程来计算 —— 不使用斜率

如果已知直线上的两个点坐标 pt1 和 pt2,可以通过参数方程来计算直线上任意两个点的坐标。参数方程表示如下:

在这里插入图片描述

#include <opencv2/opencv.hpp>

using namespace cv;

void getPointsOnLine(Point2f pt1, Point2f pt2, float x1, float x2, Point2f& pts1, Point2f& pts2) {
    // 计算参数 t
    float t1 = (x1 - pt1.x) / (pt2.x - pt1.x);
    float t2 = (x2 - pt1.x) / (pt2.x - pt1.x);

    // 根据参数方程计算对应的两个坐标点
    pts1 = pt1 + t1 * (pt2 - pt1);
    pts2 = pt1 + t2 * (pt2 - pt1);
}

int main() {
    // 已知直线上的两个点坐标
    Point2f pt1(10, 20);
    Point2f pt2(50, 80);

    // 输入的 x1 和 x2 值
    float x1 = 15;
    float x2 = 60;

    // 得到 x1 和 x2 对应的两个坐标点
    Point2f pts1, pts2;
    getPointsOnLine(pt1, pt2, x1, x2, pts1, pts2);

    // 输出结果
    std::cout << "Point 1 on line: (" << pts1.x << ", " << pts1.y << ")" << std::endl;
    std::cout << "Point 2 on line: (" << pts2.x << ", " << pts2.y << ")" << std::endl;

    return 0;
}

这段代码中,getPointsOnLine() 函数计算了给定直线上的两个点坐标 pt1 和 pt2,以及输入的 x1 和 x2 值,对应的两个坐标点 pts1 和 pts2。

2.3方向向量线来计算 —— 不使用斜率

在这里插入图片描述

#include <opencv2/opencv.hpp>

using namespace cv;

void getPointsOnLine(Point2f pt1, Point2f pt2, float x1, float x2, Point2f& pts1, Point2f& pts2) {
    // 计算从 pt1 到 pt2 的向量
    Point2f vec = pt2 - pt1;

    // 计算向量长度
    float len = norm(vec);

    // 计算对应的 x1 和 x2 的向量长度
    float len_x1 = (x1 - pt1.x) / (pt2.x - pt1.x) * len;
    float len_x2 = (x2 - pt1.x) / (pt2.x - pt1.x) * len;

    // 计算新的点坐标
    pts1 = pt1 + (vec / len) * len_x1;
    pts2 = pt1 + (vec / len) * len_x2;
}

int main() {
    // 已知直线上的两个点坐标
    Point2f pt1(10, 20);
    Point2f pt2(50, 80);

    // 输入的 x1 和 x2 值
    float x1 = 15;
    float x2 = 60;

    // 得到 x1 和 x2 对应的两个坐标点
    Point2f pts1, pts2;
    getPointsOnLine(pt1, pt2, x1, x2, pts1, pts2);

    // 输出结果
    std::cout << "Point 1 on line: (" << pts1.x << ", " << pts1.y << ")" << std::endl;
    std::cout << "Point 2 on line: (" << pts2.x << ", " << pts2.y << ")" << std::endl;

    return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

R-G-B

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值