python - 如何计算由端点和弧上点给出的两条弧的交点?

标签 python intersection

用 3 个点设置 2 条弧:2 个边界和弧中的点(了解点之间的圆的哪一侧是弧) 所以我需要在python上编写圆弧相交代码

def get_arc_sortbased(data, break_angle):
  points = data.loc[:,'x':]
  angles = points.apply(convert_to_angle,axis=1)
  points['angles'] = angles
  modes = get_mode_angle(points.loc[:,'angles'],radius=2).tolist()
  print('MODES')
  print(modes)
  points = points.sort_values(by=['angles'])
  point_lst = points['angles'].tolist()
  arcs = []
  for mode in modes:
    cent = point_lst[bs.bisect_right(point_lst, mode)]
    end_1 = find_arc_end(point_lst, mode, break_angle)
    end_2 = find_arc_end(point_lst, mode, break_angle, direction='clockwise', endPoint=end_1)
    arcs.append([end_1, cent, end_2])
  return arcs

最佳答案

这是使用 SymPy 的解决方案,Python 的符号数学库。首先构造两个圆,并计算它们的交点。交点可以是一个整圆(当两个圆相同时)、两个点、一个点(相切圆)或空。

基本思想是,当交点位于圆弧边界定义的线的同一侧时,作为第三点,则交点属于圆弧。

代码中没有解决交集是完整圆的情况。那么,存在三种可能性:弧线不重叠、它们恰好在一个点(公共(public)端点)处重叠、或者它们作为弧线重叠。重叠弧将以 4 个端点中的 2 个为边界。当现有的“第三”点不属于重叠时,可能必须寻找新的“第三”点。请注意,在浮点值坐标的情况下,重叠弧的情况会非常棘手,并且存在精度错误。

from sympy.geometry import Point, Circle, Line
from sympy.parsing.sympy_parser import parse_expr

def signed_distance(line, pnt):
    # find the signed distance between a line and a point by substituting the point into the line equation
    # note that this distance is not yet normalized, as we are only interested in the sign
    assert isinstance(line, Line) and isinstance(pnt, Point)
    eq = parse_expr(str(line.equation()), local_dict={'x':pnt.x, 'y':pnt.y})
    return eq.simplify()

def are_at_same_side(line, pnt1, pnt2):
    return signed_distance(line, pnt1) * signed_distance(line, pnt2) >= 0

p1 = Point(1, 4) # suppose the arc segment is defined by p1 and p2 as endpoints, and containing p3
p2 = Point(3, 2)
p3 = Point(1, 2)
q1 = Point(2, 3)
q2 = Point(4, 1)
q3 = Point(2, 1)
cp = Circle(p1, p2, p3)  # the circle defined by the three points
cq = Circle(q1, q2, q3)
inters = cp.intersection(cq) # intersection between the 2 circles
if isinstance(inters, Circle):
    pass # TODO: the two arcs overlap
elif len(inters) == 2:
    i1, i2 = inters
elif len(inters) == 1:
    i1 = inters[0]

# line connecting the two end points; if the third point and an intersection point lie
# on the same side of the line, then the intersection point is on the arc
lp = Line(p1, p2)
lq = Line(q1, q2)

if isinstance(inters, Circle):
    solutions = [] # TODO: the two arcs overlap
else:
    solutions = [(i1.evalf().x, i1.evalf().y) for i1 in inters
                 if i1 is not None and are_at_same_side(lp, p3, i1) and are_at_same_side(lq, q3, i1)]
print(solutions)

关于python - 如何计算由端点和弧上点给出的两条弧的交点?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58867068/

相关文章:

python - 属性错误 : 'NoneType' object has no attribute 'delete'

python - 如何在Python中实现动态路由?

sorting - 如何在 python 中使用排序输出进行 izip 压缩?

python - 取消堆叠多索引数据帧

C#: 2D sub-Tile Line 相交

python - VSCode集成了源代码控制和预提交

JavaFx Shape Intersect 始终返回 false/true

objective-c - 图形 - 我如何知道一条线是否在屏幕上可见(考虑到它的宽度)

R:跨多个向量的非共享元素(与相交相反)

list - 如何在 OCaml 中交叉两个列表?