计算几何基本模板

待更新。。。

#include<iostream>
#include<cmath>
#include<algorithm>
using namespace std;
const double PI = acos(-1);
const double EPS = 1e-8;//实数精度
//点结构类型
struct Point{
	double x, y;
	Point(double a = 0, double b = 0){ x = a; y = b; }
};
//线段结构类型
struct LineSeg{
	Point s, e;
	LineSeg();
	LineSeg(Point a, Point b): s(a), e(b){}
};
struct Line{//直线结构类型
	//直线a*x+b*y+c=0 (a>=0)
	double a, b, c;
};

Point operator-(Point a, Point b){
	return Point(a.x - b.x, a.y - b.y);
}
//重载==,判断点a,b是否相等
bool operator==(Point a, Point b){
	return abs(a.x - b.x) < EPS&&abs(a.y - b.y) < EPS;
}
//比较实数r1与r2的大小关系
int RlCmp(double r1, double r2 = 0){
	if (abs(r1 - r2) < EPS)
		return 0;
	return r1>r2 ? 1 : -1;
}

//先比较横坐标再比较纵坐标,确定顺序,一般用在sort中
bool Cmp(Point a, Point b){
	if (abs(a.x - b.x)<EPS)
		return a.y < b.y;
	else
		return a.x < b.x;
}
//返回两点间的距离
double Distance(Point a, Point b){
	return sqrt((a.x - b.x)*(a.x - b.x) + (a.y - b.y)*(a.y - b.y));
}
//返回向量p1-p0和p2-p0的点积
double Dot(Point p0, Point p1, Point p2){
	Point a = p1 - p0;
	Point b = p2 - p0;
	return a.x*b.x + a.y*b.y;
}
//返回向量p1-p0和p2-p0的叉积
double Cross(Point p0, Point p1, Point p2){
	Point a = p1 - p0;
	Point b = p2 - p0;
	return a.x*b.y - b.x*a.y;
}
//判断点p是否规范在线段L上(不包括端点)
bool Standard_Online(LineSeg L, Point p){
	return RlCmp(Cross(L.s, L.e, p)) == 0 &&
		RlCmp(Dot(p, L.s, L.e))< 0;
}
//判断点p是在线段L上(包括端点)
bool Standard_Online(LineSeg L, Point p){
	return RlCmp(Cross(L.s, L.e, p)) == 0 &&
		RlCmp(Dot(p, L.s, L.e))<=0;
}
//返回将点p沿着原点逆时针旋转alpha(弧度制)角度得到的点
Point Rotate(Point p,double alpha=PI/2){
	return Point(p.x*cos(alpha) - p.y*sin(alpha), p.x*sin(alpha) + p.y*cos(alpha));
}
//判断线段L1与线段L2是否相交(包括交点在线段上)
bool Intersect(LineSeg L1, LineSeg L2){
	//排斥实验和跨立实验
	return max(L1.s.x, L1.e.x) >= min(L2.s.x, L2.e.x)
		&& min(L1.s.x, L1.e.x) <= max(L2.s.x, L2.e.x)
		&& max(L1.s.y, L1.e.y) >= min(L2.s.y, L2.e.y)
		&& min(L1.s.y, L1.e.y) <= max(L2.s.y, L2.e.y)
		&& Cross(L1.s, L1.e, L2.s)*Cross(L1.s, L1.e, L2.e) <= 0
		&& Cross(L2.s, L2.e, L1.s)*Cross(L2.s, L2.e, L1.e) <= 0;
}
//判断线段L1与L2是否规范相交
bool Standard_Intersect(LineSeg L1, LineSeg L2){
	return RlCmp((Cross(L1.s, L1.e, L2.s)*Cross(L1.s, L1.e, L2.e))) < 0
		&& RlCmp((Cross(L2.s, L2.e, L1.s)*Cross(L2.s, L2.e, L1.e)))< 0;
}
//两不同点a,b来构造直线
Line MakeLine(Point a, Point b){
	Line L;
	L.a = (b.y -a.y);
	L.b = (a.x - b.x);
	L.c = (b.x*a.y - a.x*b.y);
	if (L.a < 0){  //保准x系数大于等于0
		L.a = -L.a;
		L.b = -L.b;
		L.c = -L.c;
	}
	return L;
}
//判直线X,Y是否相交,相交返回true和交点
bool LineIntersect(Line X, Line Y, Point&P){
	double d = X.a*Y.b - Y.a*X.b;
	if (d == 0) //直线平行或者重合
		return false;
	P.x = (X.b*Y.c - Y.b*X.c) / d;
	P.y = (X.c*Y.a - Y.c*X.a) / d;
	return true;
}

  

时间: 2024-10-13 12:03:11

计算几何基本模板的相关文章

计算几何-圆 模板 训练指南267

#include #include #include #include #include #include #include #include #include #include #define MM(a) memset(a,0,sizeof(a)) typedef long long ll; typedef unsigned long long ULL; const double eps = 1e-10; const int inf = 0x3f3f3f3f; using namespace

计算几何 --- 凸包 模板

//Memory Time // 1347K 0MS // by : Snarl_jsb #include<algorithm> #include<cstdio> #include<cstring> #include<cstdlib> #include<iostream> #include<vector> #include<queue> #include<stack> #include<map> #

计算几何入门模板(持续更新)

我也算是刚入门计算几何吧,想写一篇入门的模板,让那些和我一样刚入门的人都能看懂就好. 首先要有一些理论知识,这可以百度,我就不多说了,通过百度,你要知道: ①叉积可以判断3个点共线,还可以判断2个点构成直线,第3个点在直线的左边还是右边. ②判断两条线段相交要有2个条件,一个是矩形的什么定理(名字太长,忘了)另一个就是4个点的叉积相乘小于0(也就是异号) 之后就可以看下我收集的简单的模板了. #include <map> #include <set> #include <li

计算几何好模板

来自九野大神的博 #include <cstdio> #include <cstdlib> #include <cstring> #include <algorithm> #include <cmath> using namespace std; const double EPS = 1e-9; const int MAXN = 40; struct Point3 //空间点 { double x, y, z; Point3( double x=

计算几何 部分模板

1 struct vector 2 { 3 double x,y; 4 vector (double X=0,double Y=0) 5 { 6 x=X,y=Y; 7 } 8 } 9 typedef vector point; 向量四则运算 1 vector operator + (vector a,vector b) {return vector (a.x+b.x,a.y+b.y); } 2 vector operator - (vector a,vector b) {return vecto

hihocoder #1040 矩形判断(计算几何问题 给8个点的坐标,能否成为一个矩形 【模板思路】)

#1040 : 矩形判断 时间限制:1000ms 单点时限:1000ms 内存限制:256MB 描述 给出平面上4条线段,判断这4条线段是否恰好围成一个面积大于0的矩形. 输入 输入第一行是一个整数T(1<=T<=100),代表测试数据的数量. 每组数据包含4行,每行包含4个整数x1, y1, x2, y2 (0 <= x1, y1, x2, y2 <= 100000):其中(x1, y1), (x2,y2)代表一条线段的两个端点. 输出 每组数据输出一行YES或者NO,表示输入的

2015年ACM长春区域赛比赛感悟

距离长春区域赛结束已经4天了,是时候整理一下这次比赛的点点滴滴了. 也是在比赛前一周才得到通知要我参加长春区域赛,当时也是既兴奋又感到有很大的压力,毕竟我的第一场比赛就是区域赛水平,还是很有挑战性的.在接到通知后,我便开始临阵抱佛脚,课也不怎么听了,上课把时间全都用在了看各种算法上,回到实验室便整理模板.开cf练手.在去比赛前,已经将所看过的算法模板都整理好了. 周五上午9点三刻左右,我们便出发了,需要经历12个小时才能到达我们此次的目的地——长春,途中我还将计算几何稍微看了一下.直到晚上11点

【HDOJ】1348 Wall

计算几何-凸包模板题目,Graham算法解. 1 /* 1348 */ 2 #include <iostream> 3 #include <cstdio> 4 #include <cstring> 5 #include <cstdlib> 6 #include <cmath> 7 #include <algorithm> 8 using namespace std; 9 10 #define MAXN 1005 11 12 typed

计算几何 部分常用函数模板

来自<算法竞赛入门经典-训练指南> 刘汝佳/陈峰 清华大学出版社 #include <iostream> #include <cstdio> #include <cstdlib> #include <cstring> #include <algorithm> #include <cmath> using namespace std; const double eps = 1e-8; int dcmp(double x) /