简体   繁体   English

查找椭圆和直线之间的交点

[英]Finding intersection between ellipse and a line

I am trying to find intersection points between an elipse and a line, but seem to be unable to do so. 我试图找到椭圆和直线之间的交点,但似乎无法做到。 I have tried two approaches, one with shapely by trying to find intersection between LineString and LinearRing as in the code bellow, but did not get any usable values out of it. 我尝试了两种方法,一种通过尝试在代码波纹管中找到LineString和LinearRing之间的交点来进行整形,但是并没有从中获得任何可用的值。 One of the problems, is the elipse will always be off center and at an small or high angle 问题之一是椭圆形将始终偏离中心并以小角度或大角度出现

  # -*- coding: utf-8 -*-
"""
Created on Mon Aug 19 17:38:55 2013

@author: adudchenko
"""
from pylab import *
import numpy as np
from shapely.geometry.polygon import LinearRing
from shapely.geometry import LineString
def ellipse_polyline(ellipses, n=100):
    t = np.linspace(0, 2*np.pi, n, endpoint=False)
    st = np.sin(t)
    ct = np.cos(t)
    result = []
    for x0, y0, a, b, angle in ellipses:
        angle = np.deg2rad(angle)
        sa = np.sin(angle)
        ca = np.cos(angle)
        p = np.empty((n, 2))
        p[:, 0] = x0 + a * ca * ct - b * sa * st
        p[:, 1] = y0 + a * sa * ct + b * ca * st
        result.append(p)
    return result

def intersections(a, line):
    ea = LinearRing(a)
    eb = LinearRing(b)
    mp = ea.intersection(eb)
    print mp
    x = [p.x for p in mp]
    y = [p.y for p in mp]
    return x, y

ellipses = [(1, 1, 2, 1, 45), (2, 0.5, 5, 1.5, -30)]
a, b = ellipse_polyline(ellipses)
line=LineString([[0,0],[4,4]])
x, y = intersections(a, line)
figure()
plot(x, y, "o")
plot(a[:,0], a[:,1])
plot(b[:,0], b[:,1])
show()

I also tried using fsolve as in example bellow, but it finds the wrong intersect points ( or actually one wrong point. 我也尝试在下面的示例中使用fsolve,但是它找到了错误的相交点(或者实际上是一个错误的点)。

from pylab import *
from scipy.optimize import fsolve
import numpy as np

def ellipse_polyline(ellipses, n=100):
    t = np.linspace(0, 2*np.pi, n, endpoint=False)
    st = np.sin(t)
    ct = np.cos(t)
    result = []
    for x0, y0, a, b, angle in ellipses:
        angle = np.deg2rad(angle)
        sa = np.sin(angle)
        ca = np.cos(angle)
        p = np.empty((n, 2))
        p[:, 0] = x0 + a * ca * np.cos(t) - b * sa * np.sin(t)
        p[:, 1] = y0 + a * sa * np.cos(t) + b * ca * np.sin(t)
        result.append(p)
    return result
def ellipse_line(txy):
    t,x,y=txy
    x0, y0, a, b, angle,m,lb=1, 1, 2, 1, 45,0.5,0
    sa = np.sin(angle)
    ca = np.cos(angle)
    return (x0 + a * ca * np.cos(t) - b * sa * np.sin(t)-x,y0 + a * sa * np.cos(t) + b * ca * np.sin(t)-y,m*x+lb-y) 
a,b= ellipse_polyline([(1, 1, 2, 1, 45), (2, 0.5, 5, 1.5, -30)])
t,y,x=fsolve(ellipse_line,(0,0,0))
print t,y,x
#print a[:,0]
m=0.5
bl=0
xl,yl=[],[]
for i in range(10):
    xl.append(i)
    yl.append(m*i+bl)
figure()
plot(x, y, "o")
plot(a[:,0], a[:,1])
plot(xl,yl)

Any help would be appriceated? 有什么帮助吗?

With the Shapely part, def intersections(a, line) can be fixed. 使用Shapely部分,可以固定def intersections(a, line) First, there is an error, where it references a global b instead of using the line parameter, which is ignored. 首先,出现错误,它引用全局b而不是使用line参数,该错误被忽略。 Thus the comparison is between the two ellipses a and b , and not between each ellipse to line , as I think is intended. 因此,比较是在两个椭圆ab之间进行的,而不是每个椭圆到line之间的比较,这是我认为的预期。

Also, the intersection between two lines can be one of several outcomes: an empty set, a point (1 intersection) a multipoint (more than 1 intersection), a linestring (if any part(s) of the linestrings overlap and are parallel to each other), or a collection of points and lines. 此外,两条线之间的交点可以是以下几种结果之一:空集,一个点(1个交点),多点(1个以上的交点),线串(如果线串的任何部分重叠并且平行于彼此)或点和线的集合。 Assuming only the first three outcomes: 仅假设前三个结果:

def intersections(a, line):
    ea = LinearRing(a)
    mp = ea.intersection(line)
    if mp.is_empty:
        print('Geometries do not intersect')
        return [], []
    elif mp.geom_type == 'Point':
        return [mp.x], [mp.y]
    elif mp.geom_type == 'MultiPoint':
        return [p.x for p in mp], [p.y for p in mp]
    else:
        raise ValueError('something unexpected: ' + mp.geom_type)

So now these look correct: 所以现在这些看起来正确了:

>>> intersections(a, line)
([2.414213562373095], [2.414213562373095])
>>> intersections(b, line)
([0.0006681263405436677, 2.135895843256409], [0.0006681263405436642, 2.135895843256409])

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM