Nooby help

87 views
Skip to first unread message

Kevin Pauba

unread,
Feb 23, 2017, 12:54:12 AM2/23/17
to sympy
I'm trying to wrap my brain around sympy and am looking for a little help.

Let's say I have a line 'y=m*x' (y-intercept is zero).  Let's also say I have a circle of radius 'r' whose center is constrained to be along a horizontal line a specific distance 'd' below the x-axis.
Given m, r and d, how might I code sympy to determine the circle's x-value where the given line is tangent to the circle (i'm only interested in the tangent on the left side of the circle).  I also would like to determine the (x,y) of the tangent point.

Feel free to nudge me in the right direction if you don't have the time to offer a more complete solution.

For those interested, my interest is related to the design a cam profile that uses a roller-type follower.

Michele Zaffalon

unread,
Feb 23, 2017, 1:40:17 AM2/23/17
to sympy
This is how I would do analytically: the equation for the circle is (x-d)^2 + (y-y0)^2 = r^2, a circle of radius `r`, centered at `(d,y0)`. You impose that `y` that belongs to the circle, belongs to the line as well. To do this, you substitute the equation for the line in that for the circle and you obtain `expr` below (y -> mx).
If you solve this second order equation, you find two solutions because in general, the line crosses the circle in two points (or never). You want these two points to be coincident because this is an alternative definition of tangent and you solve for `y0`. There are again two solutions, one with the circle to the right of the line, one to the left. You should pick the correct one: on my computer, this is the second solution.
If you now substitute this into any of `sols`, you will find your tangent `x` point.
Does this help?

x, y, d, y0 = symbols("x, y, d, y0", real=True)
m
, r = symbols("m, r", positive=True)
expr
= (x+d)**2 + (m*x-y0)**2 - r**2
sols
= solve(expr, x)
y0_sols
= solve(sols[0] - sols[1], y0)
simplify
(sols[1].subs(y0, y0_sol[1]))

Michele Zaffalon

unread,
Feb 23, 2017, 1:49:58 AM2/23/17
to sympy
Another quicker way is to impose that the circle slope is the same as the line.
The first expression is the explicit equation for the top part of the circle. Then I impose that the slope is that of the line and I find the tangent `x` position.

y = y0 + sqrt(r**2 - (x-d)**2)
solve
(diff(y,x) - m, x)

Kevin Pauba

unread,
Feb 23, 2017, 7:40:21 AM2/23/17
to sympy
Wow, thanks Michele!

Having two solutions will help me to understand sympy even better.  I really, really appreciate your replies and I'll be plugging in this code interactively line-by-line along with the docs to see how every argument and line contributes to the solution.

Michele Zaffalon

unread,
Feb 26, 2017, 1:15:32 PM2/26/17
to sympy
Hi Kevin,
I mixed up the coordinates and the solution I gave you is wrong. To make it up to you, here is the complete (and this time I hope correct) solution.

from
sympy import init_session
init_session
()
y
, x0 = symbols("y, x0", real=True)
# I define d positive, but the equation for the circle is
# (x-x0)^2 + (y+d)^2 = r^2
d
, m, r = symbols("d, m, r", positive=True)

#method I
# write explicit equation for circle
x
= x0 - sqrt(r**2 - (y + d)**2)
# find the point on circle for which slope dx/dy = 1/m
# is the same as line x = 1/m * y
y_v
= solve(diff(x,y) - 1/m, y)[0]
# find x coordinate of tangent
x_v
= y_v / m
# from x = x0 - sqrt(r**2 - (y + d)**2)
# find center of circle

x0_v
= simplify(x_v + sqrt(r**2 - (y_v + d)**2))

# check
x
= symbols("x", real=True)
y
= -d + sqrt(r**2 - (x - x0_v)**2)
# the derivative at point x_v should be m

diff
(y, x).subs(x, x_v)

Kevin Pauba

unread,
Feb 26, 2017, 8:42:41 PM2/26/17
to sympy
Thanks, Michele.

With your earlier post, I noticed the difference in the solution and I was able to modify the code to work as I needed -- I figured I just didn't describe it well enough.  I had everything working perfectly on Friday.

Thanks again for your assistance.

Michele Zaffalon

unread,
Feb 26, 2017, 11:59:28 PM2/26/17
to sympy
Kevin,

Your description was good; my hands were faster than my brain.
Good to hear that you managed to solve _despite_ my help.

michele
Reply all
Reply to author
Forward
0 new messages