c++ 多边形求交集代码(凸多边形与凹多边形的交集)

多边形求交集cpp代码

凸多边形与凹多边形的交集:c++ 多边形求交集代码(凸多边形与凹多边形的交集)
凸多边形与凸多边形的交集:c++ 多边形求交集代码(凸多边形与凸多边形的交集)
在这里插入图片描述

#include "stdafx.h"
#include <iostream>
#include <stdlib.h>

#include <opencv2\opencv.hpp>

using namespace std;
using namespace cv;

#define FREESPACENUM 64

//计算多边形面积
float PolygonArea(Point2f p[], int n)
{
	if (n < 3) return 0.0;
	float s = p[0].y * (p[n - 1].x - p[1].x);
	p[n] = p[0];
	for (int i = 1; i < n; ++i)
	{
		s += p[i].y * (p[i - 1].x - p[i + 1].x);
	}
	return fabs(s * 0.5);
}

int pointLineRelationship(int pt1x,int pt1y, int pt2x, int pt2y, int &pt0x, int &pt0y)
{
	//iValue=0,点在分割线上,iValue>0,点在直线Pt3顺时针那侧,iValue<0,点在直线Pt3逆时针那侧,
	return((pt2y - pt1y) * pt0x + (pt1x - pt2x) * pt0y + (pt2x*pt1y - pt1x*pt2y));
}

bool intersect(int pt1x, int pt1y, int pt2x, int pt2y, int pt3x, int pt3y, int pt4x, int pt4y, int &ptNodex, int &ptNodey)
{
	int ax = pt2x - pt1x, ay = pt2y - pt1y;
	int bx = pt3x - pt4x, by = pt3y - pt4y;
	int cx = pt1x - pt3x, cy = pt1y - pt3y;

	float fDenominator = ay * bx - ax * by;
	if (fDenominator == 0) return false;

	float fReciprocal = 1 / fDenominator;
	float na = (by * cx - bx * cy) * fReciprocal;
	ptNodex = ax * na + pt1x;
	ptNodey = ay * na + pt1y;

	if (na < 0 || na > 1) return true;

	float nb = (ax * cy - ay * cx) * fReciprocal;
	if (nb < 0 || nb > 1) return true;

	return true;
}


int main()
{
	Mat img = imread("7487939.jpg");

	// init park
	vector<vector<int>> parkList(6);
	parkList[0] = {160,180,140,90,24,89,23,171 };
	parkList[1] = {192,458,188,368,27,362,10,480};
	parkList[2] = {451,173,444,332,617,318,621,199};
	parkList[3] = {439,372,429,478,620,446,632,320};
	parkList[4] = {427,490,358,500,336,616,476,616};
	parkList[5] = {248,505,158,486,118,612,236,620};

	for (vector<int> park: parkList)
	{
		cv::line(img,Point2i(park[0], park[1]), Point2i(park[2], park[3]), Scalar(0, 0,255),2,8);
		cv::line(img, Point2i(park[2], park[3]), Point2i(park[4], park[5]), Scalar(0, 0, 255), 2, 8);
		cv::line(img, Point2i(park[4], park[5]), Point2i(park[6], park[7]), Scalar(0, 0, 255), 2, 8);
		cv::line(img, Point2i(park[6], park[7]), Point2i(park[0], park[1]), Scalar(0, 0, 255), 2, 8);
	}

	// init freespace
	vector<Point2i> leftFreespace, rightFreespace, backFreespace;
	for (int i=0;i<FREESPACENUM;++i)
	{
		leftFreespace.push_back(Point2i(rand() % 200, 640-i * 10));
	}

	for (int i = 0; i < FREESPACENUM; ++i)
	{
		cv::circle(img, Point2i(leftFreespace[i].x, leftFreespace[i].y), 2, Scalar(0, 255, 0),4,8);
	}
	for (int i = 0; i < FREESPACENUM-1; ++i)
	{
		cv::line(img, Point2i(leftFreespace[i].x, leftFreespace[i].y), Point2i(leftFreespace[i+1].x, leftFreespace[i+1].y), Scalar(0, 255, 0), 2, 8);
	}

	//begin
	int poly_j_begin = -1, poly_j_end = -1;
	int n_flag = -1; 
	int min_x, max_x, min_y, max_y;
	int min_x_p0167, max_x_p0167, min_y_p0167, max_y_p0167;
	int min_x_p0123, max_x_p0123, min_y_p0123, max_y_p0123;
	int min_x_p2345, max_x_p2345, min_y_p2345, max_y_p2345;
	int min_x_p4567, max_x_p4567, min_y_p4567, max_y_p4567;
	int min_x_freespace, max_x_freespace, min_y_freespace, max_y_freespace;
	int cross_x_p0167, cross_y_p0167, cross_x_p0123, cross_y_p0123, cross_x_p2345, cross_y_p2345, cross_x_p4567=0, cross_y_p4567=0/*, cross_x, cross_y*/;
	float fAllArea = 0.f, fParkArea=0.f;
	Point2f pParkSet[10];
	Point2f pPolygonSet[FREESPACENUM];
	int pPolygonSetAttribute[FREESPACENUM];
	int pPolygonIndex;
	for (int i= parkList.size()-1;i>=0;--i)
	{
		pParkSet[0] = Point2f(parkList[i][0], parkList[i][1]);
		pParkSet[1] = Point2f(parkList[i][2], parkList[i][3]);
		pParkSet[2] = Point2f(parkList[i][4], parkList[i][5]);
		pParkSet[3] = Point2f(parkList[i][6], parkList[i][7]);

		fParkArea = PolygonArea(pParkSet,4);

		poly_j_begin = -1, poly_j_end = -1;
		min_x = min(min(parkList[i][0], parkList[i][2]), min(parkList[i][4], parkList[i][6]));
		max_x = max(max(parkList[i][0], parkList[i][2]), max(parkList[i][4], parkList[i][6]));
		min_y = min(min(parkList[i][1], parkList[i][3]), min(parkList[i][5], parkList[i][7]));
		max_y = max(max(parkList[i][1], parkList[i][3]), max(parkList[i][5], parkList[i][7]));

		min_x_p0167 = min(parkList[i][0], parkList[i][6]);
		max_x_p0167 = max(parkList[i][0], parkList[i][6]);
		min_y_p0167 = min(parkList[i][1], parkList[i][7]);
		max_y_p0167 = max(parkList[i][1], parkList[i][7]);

		min_x_p0123 = min(parkList[i][0], parkList[i][2]);
		max_x_p0123 = max(parkList[i][0], parkList[i][2]);
		min_y_p0123 = min(parkList[i][1], parkList[i][3]);
		max_y_p0123 = max(parkList[i][1], parkList[i][3]);

		min_x_p2345 = min(parkList[i][2], parkList[i][4]);
		max_x_p2345 = max(parkList[i][2], parkList[i][4]);
		min_y_p2345 = min(parkList[i][3], parkList[i][5]);
		max_y_p2345 = max(parkList[i][3], parkList[i][5]);

		min_x_p4567 = min(parkList[i][4], parkList[i][6]);
		max_x_p4567 = max(parkList[i][4], parkList[i][6]);
		min_y_p4567 = min(parkList[i][5], parkList[i][7]);
		max_y_p4567 = max(parkList[i][5], parkList[i][7]);

		pPolygonIndex = 0;
		for (int j=0;j<FREESPACENUM-1;++j)
		{
			//cout << j << endl;
			if (min_x <=leftFreespace[j].x&&max_x >=leftFreespace[j].x&& min_y <=leftFreespace[j].y&& max_y >=leftFreespace[j].y)
			{
				n_flag = 0;
				//cout <<j<<" "<< leftFreespace[j].x << " " << leftFreespace[j].y << endl;
				min_x_freespace = min(leftFreespace[j].x, leftFreespace[j + 1].x);
				max_x_freespace = max(leftFreespace[j].x, leftFreespace[j + 1].x);
				min_y_freespace = min(leftFreespace[j].y, leftFreespace[j + 1].y);
				max_y_freespace = max(leftFreespace[j].y, leftFreespace[j + 1].y);

				//01-67
				intersect(parkList[i][0], parkList[i][1], parkList[i][6], parkList[i][7], 
					leftFreespace[j].x, leftFreespace[j].y,leftFreespace[j+1].x, leftFreespace[j+1].y, cross_x_p0167, cross_y_p0167);
				//01-67边有交点
				if (min_x_p0167 <= cross_x_p0167&& max_x_p0167 >= cross_x_p0167 && min_y_p0167 <= cross_y_p0167 && max_y_p0167 >= cross_y_p0167
					&& min_x_freespace <= cross_x_p0167&& max_x_freespace >= cross_x_p0167 && min_y_freespace <= cross_y_p0167&& max_y_freespace >= cross_y_p0167)
				{
					cout<<"p0167 ===== "<< cross_x_p0167 << " " << cross_y_p0167 << endl;
					n_flag = 1;

					pPolygonSet[pPolygonIndex] = Point2f(cross_x_p0167, cross_y_p0167);
					pPolygonSetAttribute[pPolygonIndex] = n_flag;
					++pPolygonIndex;
				}

				//01-23
				intersect(parkList[i][0], parkList[i][1], parkList[i][2], parkList[i][3], 
					leftFreespace[j].x, leftFreespace[j].y,leftFreespace[j + 1].x, leftFreespace[j + 1].y, cross_x_p0123, cross_y_p0123);
				//01-23边有交点
				if (min_x_p0123 <= cross_x_p0123&& max_x_p0123  >= cross_x_p0123 && min_y_p0123 <= cross_y_p0123 && max_y_p0123 >= cross_y_p0123
					&& min_x_freespace <= cross_x_p0123 && max_x_freespace >= cross_x_p0123 && min_y_freespace <= cross_y_p0123 && max_y_freespace >= cross_y_p0123)
				{
					cout << "p0123 ===== " << cross_x_p0123 << " " << cross_y_p0123 << endl;
					n_flag = 2;

					pPolygonSet[pPolygonIndex] = Point2f(cross_x_p0123, cross_y_p0123);
					pPolygonSetAttribute[pPolygonIndex] = n_flag;
					++pPolygonIndex;
				}

				//23-45
				intersect(parkList[i][2], parkList[i][3], parkList[i][4], parkList[i][5], 
					leftFreespace[j].x, leftFreespace[j].y,leftFreespace[j + 1].x, leftFreespace[j + 1].y, cross_x_p2345, cross_y_p2345);
				//23-45边有交点
				if (min_x_p2345 <= cross_x_p2345 && max_x_p2345 >= cross_x_p2345 && min_y_p2345 <= cross_y_p2345 && max_y_p2345 >= cross_y_p2345
					&& min_x_freespace <= cross_x_p2345 && max_x_freespace >= cross_x_p2345 && min_y_freespace <= cross_y_p2345 && max_y_freespace >= cross_y_p2345)
				{
					cout << "p2345 ===== " << cross_x_p2345 << " " << cross_y_p2345 << endl;
					n_flag = 3;

					pPolygonSet[pPolygonIndex] = Point2f(cross_x_p2345, cross_y_p2345);
					pPolygonSetAttribute[pPolygonIndex] = n_flag;
					++pPolygonIndex;
				}

				//45-67
				intersect(parkList[i][4], parkList[i][5], parkList[i][6], parkList[i][7], 
					leftFreespace[j].x, leftFreespace[j].y,leftFreespace[j + 1].x, leftFreespace[j + 1].y, cross_x_p4567, cross_y_p4567);
				//45-67边有交点
				if (min_x_p4567 <= cross_x_p4567 && max_x_p4567 >= cross_x_p4567 && min_y_p4567 <= cross_y_p4567 && max_y_p4567 >= cross_y_p4567
					&& min_x_freespace <= cross_x_p4567 && max_x_freespace >= cross_x_p4567 && min_y_freespace <= cross_y_p4567 && max_y_freespace >= cross_y_p4567)
				{
					cout << "p4567 ===== " << cross_x_p4567 << " " << cross_y_p4567 << endl;
					n_flag = 4;

					pPolygonSet[pPolygonIndex] = Point2f(cross_x_p4567, cross_y_p4567);
					pPolygonSetAttribute[pPolygonIndex] = n_flag;
					++pPolygonIndex;
				}

				if (n_flag<1)
				{
					pPolygonSet[pPolygonIndex] = Point2f(leftFreespace[j].x, leftFreespace[j].y);
					pPolygonSetAttribute[pPolygonIndex] = n_flag;
					++pPolygonIndex;
				}

			} // end if 
		}// end for

		poly_j_begin = pPolygonSetAttribute[0];
		poly_j_end = pPolygonSetAttribute[pPolygonIndex-1];
		if (poly_j_begin>-1&& poly_j_end>-1)
		{
			if (poly_j_begin == 1)
			{
				if (poly_j_end == 2)
				{
					pPolygonSet[pPolygonIndex] = pParkSet[1];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;

					pPolygonSet[pPolygonIndex] = pParkSet[2];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;

					pPolygonSet[pPolygonIndex] = pParkSet[3];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;
				}
				else if (poly_j_end == 3)
				{
					pPolygonSet[pPolygonIndex] = pParkSet[2];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;

					pPolygonSet[pPolygonIndex] = pParkSet[3];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;
				}
				else  if (poly_j_end == 4)
				{
					pPolygonSet[pPolygonIndex] = pParkSet[3];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;
				}
			}
			else if (poly_j_begin == 2)
			{
				if (poly_j_end == 1)
				{
					pPolygonSet[pPolygonIndex] = pParkSet[0];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;
				}
				else if (poly_j_end == 3)
				{
					pPolygonSet[pPolygonIndex] = pParkSet[2];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;

					pPolygonSet[pPolygonIndex] = pParkSet[3];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;

					pPolygonSet[pPolygonIndex] = pParkSet[0];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;
				}
				else if (poly_j_end == 4)
				{
					pPolygonSet[pPolygonIndex] = pParkSet[3];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;

					pPolygonSet[pPolygonIndex] = pParkSet[0];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;
				}
			}
			else if (poly_j_begin == 3)
			{
				if (poly_j_end == 1)
				{
					pPolygonSet[pPolygonIndex] = pParkSet[0];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;

					pPolygonSet[pPolygonIndex] = pParkSet[1];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;
				}
				else if (poly_j_end == 2)
				{
					pPolygonSet[pPolygonIndex] = pParkSet[1];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;
				}
				else if (poly_j_end == 4)
				{
					pPolygonSet[pPolygonIndex] = pParkSet[3];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;

					pPolygonSet[pPolygonIndex] = pParkSet[0];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;

					pPolygonSet[pPolygonIndex] = pParkSet[1];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;
				}
			}
			else
			{
				if (poly_j_end == 1)
				{
					pPolygonSet[pPolygonIndex] = pParkSet[0];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;

					pPolygonSet[pPolygonIndex] = pParkSet[1];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;

					pPolygonSet[pPolygonIndex] = pParkSet[2];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;
				}
				else if (poly_j_end == 2)
				{
					pPolygonSet[pPolygonIndex] = pParkSet[1];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;

					pPolygonSet[pPolygonIndex] = pParkSet[2];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;
				}
				else if (poly_j_end == 3)
				{
					pPolygonSet[pPolygonIndex] = pParkSet[2];
					pPolygonSetAttribute[pPolygonIndex] = -1;
					++pPolygonIndex;
				}
			}
		}

		cout << "***************" << endl;
		/*for (int n=0;n<pPolygonIndex;++n)
		{
			cout << pPolygonSet[n].x << " " << pPolygonSet[n].y << " " << pPolygonSetAttribute[n] << endl;
		}
		cout <<"---------------" <<endl;*/


		fAllArea = PolygonArea(pPolygonSet, pPolygonIndex);

		cout << fParkArea << " " << fAllArea << " "<<fAllArea / fParkArea << endl;

		cout << "---------------" << endl;
	}

	imshow("img", img);
	waitKey(0);
    return 0;
}

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

mingo_敏

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

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

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

打赏作者

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

抵扣说明:

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

余额充值