文章目录
- 前言
- 正题
- 平面运算
- 加减
- 乘积
- 常见问题
- 直线/线段规范交点
- 求垂线/点问题
- 判断点在多边形的内/外
- 求两个圆的交点
前言
因为懒得画图理解计算几何所以要来这里鼓励一下自己
以后新学的应该也会写在这里。就当我是水博客
应该都是二维的计算几何,三维的有生之年再学
公式用的不规范,感性理解的
正题
平面运算
定义两个向量a⃗=(xa,ya),b⃗=(xb,yb)\vec{a}=(x_a,y_a),\vec{b}=(x_b,y_b)a=(xa,ya),b=(xb,yb)
下方为了方便不一定会加→\rightarrow→
加减
向量加法遵循平行四边形定则,a⃗+b⃗=c⃗\vec a+\vec b=\vec ca+b=c
满足xc=xa+xb,yc=ya+ybx_c=x_a+x_b,y_c=y_a+y_bxc=xa+xb,yc=ya+yb
向量减法遵循三角形定则,a⃗−b⃗=c⃗\vec a-\vec b=\vec ca−b=c
满足xc=xa−xb,yc=ya−ybx_c=x_a-x_b,y_c=y_a-y_bxc=xa−xb,yc=ya−yb
图里a−b⃗\vec{a-b}a−b的方向反了/kk
乘积
定义∣a∣|a|∣a∣表示aaa的模长,表示向量aaa的无向长度,而aaa的模定义为有向长度
定义a∗ba*ba∗b表示aaa与bbb的点积,是bbb投影到aaa上的向量模乘上向量aaa的模。实数a∗b=xaxb+yayba*b=x_ax_b+y_ay_ba∗b=xaxb+yayb
(为了清楚我将红色线下移了一格),点积就是红色的长度乘上蓝色的长度
一般的时候点积用于判断两条直线的正反,如果两条直线方向相同则点积为正否则为负。
定义a×ba\times ba×b表示aaa与bbb的叉积,是向量a,ba,ba,b围成的平行四边形的有向面积。实数a×b=xayb−xbyaa\times b=x_ay_b-x_by_aa×b=xayb−xbya
如图所示的平行四边形的有向面积就是a×ba\times ba×b
一般用于求多边形的面积或者判断一条直线在另一条直线的左侧还是右侧。
常见问题
直线/线段规范交点
询问两条直线a:(sa,ta)a:(s_a,t_a)a:(sa,ta)与b:(sb,tb)b:(s_b,t_b)b:(sb,tb)交点时(我们用向量形式表示点坐标,再以直线上两个点表示直线)。
考虑使用面积法
如图,我们使用叉积计算由直线aaa分开的两个三角形的面积S1,S2S1,S2S1,S2
那么SO:OT=S1:S2SO:OT=S1:S2SO:OT=S1:S2然后我们又知道STSTST的线段信息就可以求出点坐标OOO的位置。
如果询问的是线段与直线的,我们加上一个叉积判断线段是否在直线的两端即可。
如果询问线段与线段的,我们就直接分别把两条线视为直线/线段进行上面的判断即可。
求垂线/点问题
给出直线lll和直线外一点PPP求它与直线lll的垂点/线
考虑点积
因为SP⃗∗ST⃗=SO∗ST\vec{SP}*\vec{ST}=SO*STSP∗ST=SO∗ST然后除以ST2ST^2ST2我们就可以得到SO:STSO:STSO:ST然后缩短STSTST一定距离就可以得到OOO点了。
当然如果只是求垂线长度的话直接用面积法也行。
判断点在多边形的内/外
第一种方法就是射线法,该点随机向一个方向射线,如果与奇数条边相交则在内,否则在外。当然这种可能会遇到的包括但不限于以下神奇情况
当然听大佬说遇到这种情况重新换个方向拉射线就好了(?
特点是运算快,精度高但是特殊情况较多
第二种方法是转角法,该点开始的射线依次转过多边形的每个顶点,如果转回来之后经过了一个圈,那么就在多边形内,否则不在
特点是比较通用
求两个圆的交点
根据余弦定理我们有CB2=AC2+AB2−2AC∗AB∗cos∠CABCB^2=AC^2+AB^2-2AC*AB*cos\angle CABCB2=AC2+AB2−2AC∗AB∗cos∠CAB
解出cos∠CABcos\angle CABcos∠CAB然后用atan2atan2atan2函数算出级角再算出方位角即可
待更新懒得更新了,计算几何爬出OI