【问题标题】:How to find the intervals that are intersection of a circle with a rectangle如何找到圆与矩形相交的间隔
【发布时间】:2020-02-02 09:10:44
【问题描述】:

我需要对圆与矩形相交并落在矩形内的弧进行积分。我可以使用shapely 包找到交点。但是,我不知道如何获得积分间隔。例如,在下图中,我的代码以弧度返回 [-2.1562, 2.1562](相对于圆心),而它应该能够自动理解落在矩形内的积分区间是 [[2.1562, 3.1415],[-3.1415, -2.1562]](假设 pi = 3.1415)。

这是另一个例子:

我的代码返回[-0.45036, -0.29576, 0.29576, 0.45036],预期的间隔将是[[0.29576, 0.45036], [-0.45036, -0.29576]]

代码也应该适用于圆所在的任何其他位置(任何半径),无论其中心是在矩形之外还是在矩形内。

这是我使用 iPython 编写的代码:

import matplotlib.pyplot as plt
import math
import numpy as np
from shapely.geometry import LineString, MultiPoint
from shapely.geometry import Polygon
from shapely.geometry import Point

# Utilities
def cart2pol(xy, center):
    x,y = xy
    x_0,y_0 = center
    rho = np.sqrt((x-x_0)**2 + (y-y_0)**2)
    phi = np.arctan2(y-y_0, x-x_0)
    return(rho, phi)

def pol2cart(rho, phi, center):
    x_0,y_0 = center 
    x = rho * np.cos(phi)+x_0
    y = rho * np.sin(phi)+y_0
    return(x, y)

def distance(A,B):
  return math.sqrt((A[0]-B[0])**2+(A[1]-B[1])**2)

#######################  
rad = 6
center = (-1,5)
p = Point(center)
c = p.buffer(rad).boundary
A = (10,0)
B = (0,0)
C = (0,10)
D = (10,10)

coords = [Point(A), Point(B), Point(C), Point(D)]
poly = MultiPoint(coords).convex_hull

i=c.intersection(poly)

lines = [LineString([A, D]), LineString([D, C]),
         LineString([C, B]), LineString([B, A])]

points = []
for l in lines:
  i = c.intersection(l) 
  if not i.is_empty:
    if i.geom_type == 'MultiPoint':
      for j in range(len(i.geoms)):
        points.append(i.geoms[j].coords[0])
    else:
      points.append(i.coords[0])

# Repeat the tangential points
for k, point in enumerate(points.copy()):
  if abs(distance(center, point)**2 + distance(point, B)**2 - distance(B, center)**2) < 1e-4:
    points.insert(k+1,point)
  elif abs(distance(center, point)**2 + distance(point, D)**2 -distance(D, center)**2) < 1e-4:
    points.insert(k+1,point)

# Sort points in polar coordinates
phis = [cart2pol(point,center)[1] for point in points]
phis.sort()
print(phis)

# Plot the shapes
x,y = c.xy
plt.plot(*c.xy)
for l in lines:
  plt.plot(*l.xy, 'b')
plt.gca().set_aspect('equal', adjustable='box')

我尝试根据交叉点的角度对交叉点进行排序,使交叉点列表中的每两个相邻项目对应一个弧。问题是当沿单位圆旋转时,从 -pi 到 pi 的角度会有跳跃。另外我不知道如何确定弧是否在​​矩形内或没有给出它的 2 个端点。

【问题讨论】:

  • 你能更好地解释一下你在做什么吗?
  • @MadPhysicist 我需要在矩形内的圆弧上计算函数的积分。但我只有交点。在第一个示例中,一个点具有负角,而另一个交点具有正角。如果我只是在这个区间内整合我的函数,我会得到一个错误的答案。 (-pi 等价于单位圆上的+pi)
  • @MadPhysicist 换句话说,我在极坐标中有一些积分,例如 integral_c f(theta) d theta 其中 c 是矩形内圆的所有弧我想找到这些弧中每一个的积分区间。

标签: python geometry computational-geometry intersection


【解决方案1】:

处理角度范围并不简单。

1) 选择一个没有歧义的表示范围,例如[-π, π) 弧度。

2) 编写一个函数,找出圆与 (h/v) 半平面的交点并返回角度区间。如果区间跨越 ±π 边界,则将其一分为二。

3) 编写一个函数来查找两个区间列表之间的交集(这是一个修改后的合并问题)。

4) 处理四个边并与生成的区间相交。

5) 可能合并跨越 ±π 边界的区间。

【讨论】:

  • 感谢您的回答。我的代码找到了圆与矩形的交点。然后我在极坐标中对这些点进行排序,其中圆心是坐标系的中心。因此我认为我实际上有间隔(排序列表中的每两个相邻点)。但是,我不知道弧是在矩形内部还是外部。我认为应该有更简单的方法。
  • @SMA.D:不,没有。
猜你喜欢
  • 2012-11-20
  • 1970-01-01
  • 2013-07-02
  • 2018-03-11
  • 1970-01-01
  • 2010-09-28
  • 1970-01-01
  • 2022-01-20
  • 2014-05-01
相关资源
最近更新 更多