我需要定义显式表达式来找到点(x1,y1)和(x2,y2),它们是半径为r(已知)和两条线(已知方程)的圆的两个切点。圆的中心(x0,y0)是不已知的,而 not 则是必需的。参见下面的图片。
对于我来说,我具有以下条件:
我计算出以下内容:
x1, y1, x2, y2 = var('x1, y1, x2, y2') # tangent points
m1, b1, m2, b2 = var('m1, b1, m2, b2') # lines' eqn
x0, y0, r = var('x0, y0, r') # cirsle's eqn
eq1 = (x1 - x0)^2 + (y1 - y0)^2 - r^2 == 0
eq2 = (x2 - x0)^2 + (y2 - y0)^2 - r^2 == 0
eq3 = y1 - m1*x1 - b1 == 0
eq4 = y2 - m2*x2 - b2 == 0
eq5 = (y1-y0)/(x1-x0) == -1/m1
eq6 = (y2-y0)/(x2-x0) == -1/m2
# unknown: x0,y0,x1,y1,x2,y2
# known: m1,b1,m2,b2,r
solve([eq1,eq2,eq3,eq4,eq5,eq6,
x1>0,y1>0,x2>0,y2>0,
m1<=0,b1>=0,m2<m1,b2>b1,
x0>x2,y0>y1,r>0],x0,y0,x1,y1,x2,y2)
为什么这不足以定义问题?
答案 0 :(得分:2)
我既不了解Sage(我认为您的代码已包含在其中)的细节,也不知道Mathematica,但我可以指出一些困难。
首先,我认为您需要将定义的数学变量“捕获”到语言变量中。所以您可能需要
x1, y1, x2, y2 = var('x1, y1, x2, y2') # tangent points
m1, b1, m2, b2 = var('m1, b1, m2, b2') # lines' eqn
x0, y0, r = var('x0, y0, r') # cirsle's eqn
接下来,您将所有方程式放入一个solve
命令中。从图中可以看到,圆上和两条线上都没有点,但是您尝试同时找到满足所有方程的所有点。您应该将单个solve
分成两个命令,每行一个。
接下来,您的要求中没有任何东西会使您的线与给定曲线相切。对于几乎任意的圆和线,可能没有一个,一个或两个交点,并且极不可能出现一个精确的点。您需要限制每条线与曲线相切。该限制很难编程,似乎比仅找到相交点还容易。您确定所使用的方法是解决问题的好方法吗?
要确保切点在第一象限中还存在其他困难,但这并不比其他困难重要。
最后,您的代码中没有任何内容可以表明您的已知值是m1, b1, m2, b2, r
,并且您希望x0, y0
退出最终表达式。 (您确实声明想要x1, y1, x2, y2
的表达式。)我不知道如何在Sage或Mathematica中这样做。
所涉及的数学问题并不那么困难。点(x0, y0)
必须位于与给定线平行的线上,并且与这些线的距离为r
。得出(x0, y0)
有4分。对于每一个点,您都会在给定的直线上找到最接近这些点(x0, y0)
的点。总共得到四个点,然后您只需在第一象限中选择一个即可。另一种更快的三角方法是找到两条给定线之间的角度,然后可以使用trig来找到所需点到相交点的距离,然后找到这些点。
您确定需要Sage / Mathematica来做到这一点吗?
答案 1 :(得分:2)
与两条给定直线在距离R处的平行线在圆心处相交。找到这一点后,将其投影在两条原始线上。
这些操作具有简单的解析表达式。
让两行分别为a'x+b'y+c'=0
,a"x+b"y+c"=0
,其中a'²+b'²=1, a"²+b"²=1
(这是比您的方程式更通用的形式)。
平行线的交点是系统的解决方案
a'x+b'y+c'-r=0
a"x+b"y+c"-r=0,
根据克莱默法则
|c'-r b'| / |a' b'| |a' c'-r| / |a' b'|
u = |c"-r b"| / |a" b"|, v = |a" c"-r| / |a" b"|
和投影的坐标简单地由
给出x' = x - a (a'u+b'v+c)
y' = y - b (a'u+b'v+c)
x" = x - a (a"u+b"v+c)
y" = y - b (a"u+b"v+c)
答案 2 :(得分:1)
将x1
,y1
,x2
和y2
计算为未知数
Clear[m1, x1, b1, m2, x2, b2, r, x0]
y1 = m1 x1 + b1;
y2 = m2 x2 + b2;
s1 = r/Sqrt[1 + 1/m1^2];
s2 = r/Sqrt[1 + 1/m2^2];
x0 = x0 /. FullSimplify@Solve[
m1 x0 + b1 + (s1 (-(1/m1)) - s1 m1) ==
m2 x0 + b2 + (s2 (-(1/m2)) - s2 m2), x0][[1]]
(-b1 + b2 + Sqrt [1 + 1 / m1 ^ 2] m1 r-Sqrt [1 + 1 / m2 ^ 2] m2 r)/(m1-m2)
y0 = FullSimplify[m1 x0 + b1 + (s1 (-(1/m1)) - s1 m1)]
(b2 m1-m2(b1 + m1(-Sqrt [1 + 1 / m1 ^ 2] + Sqrt [1 + 1 / m2 ^ 2])r))/(m1-m2)
x1 = x1 /. FullSimplify@
Solve[{(x1 - x0)^2 + (y1 - y0)^2 == r^2}, x1][[1]]
(r + m1 m2 r- Sqrt [1 + 1 / m1 ^ 2] m1(b1-b2 + Sqrt [1 + 1 / m2 ^ 2] m2 r))/(Sqrt [ 1 + 1 / m1 ^ 2] m1(m1-m2))
x2 = x2 /. FullSimplify@
Solve[{(x2 - x0)^2 + (y2 - y0)^2 == r^2}, x2][[1]]
(b2-b1(1 + m2 ^ 2)+ Sqrt [1 + 1 / m1 ^ 2] m1 r + m2(b2 m2-(Sqrt [1 + 1 / m2 ^ 2] + m1(-Sqrt [1 + 1 / m1 ^ 2] + Sqrt [1 + 1 / m2 ^ 2])m2)r))/((m1- m2)(1 + m2 ^ 2))
使用值进行测试
m1 = -0.28; b1 = 1.64; m2 = -1.08; b2 = 3.84;
r = 3.9062658021579098;
{x1, y1}
{x2, y2}
{3.81302,0.572355}
{2。,1.68}
Show[Plot[
{m1 x + b1,
m1 x + b1 + (s1 (-(1/m1)) - s1 m1),
m2 x + b2,
m2 x + b2 + (s2 (-(1/m2)) - s2 m2)}, {x, 0, 10},
PlotRange -> {{0, 10}, {0, 10}}, AspectRatio -> 1],
Graphics[Circle[{x0, y0}, r]]]