本文章所述内容仅适用于判断是否有交点,不能判断交点坐标
假设有两个标准方程椭圆,经过平移(x_0,y_0),逆时针旋转\theta°,得到椭圆:
\frac{((x-x_0)cos\theta+(y-y_0)sin\theta)^2}{a^2}+\frac{((x-x_0)sin\theta-(y-y_0))^2}{b^2}=1
我们想要将其转换为二次型方程:
(x-\mu)^TA(x-\mu)=1
接下来,定义M=\frac{A_1^{-1}}{1-s}+\frac{A_2^{-1}}{s},d=\mu_2-\mu_1
K(S)=1-d^TM^{-1}d
如果K(s)_{min} \ge 0 \ \ (s \in (0,1))则两椭圆有交点,这种方法比联立求解快得多
至于为什么这样做,我不知道,但是确实可以这样做
以下是一个Python的实现。很混乱,但是能用,建议只关心输入参数就好
输入参数分别为两个椭圆的平移、a、b、逆时针旋转弧度(不是角度)
def complex_solution(x0_1, y0_1, a1, b1, theta1, x0_2, y0_2, a2, b2, theta2):
def ellipse_param_to_invA(a, b, theta):
c, s = np.cos(theta), np.sin(theta)
R = np.array([[c, -s], [s, c]])
diag_ab = np.diag([a ** 2, b ** 2])
return R @ diag_ab @ R.T
def K_function(s, invA, invB, d):
M = invA / (1.0 - s) + invB / s
M_inv = inv(M)
return 1.0 - d @ M_inv @ d
mu1 = np.array([x0_1, y0_1])
mu2 = np.array([x0_2, y0_2])
invA1 = ellipse_param_to_invA(a1, b1, theta1)
invA2 = ellipse_param_to_invA(a2, b2, theta2)
d = mu2 - mu1
def f(s):
return K_function(s, invA1, invA2, d)
res = minimize_scalar(f, bounds=(1e-6, 1 - 1e-6), method='bounded')
K_min = res.fun
return K_min >= 0
参考文章:conic sections - Detect if two ellipses intersect - Mathematics Stack Exchange