【发布时间】:2016-01-11 04:23:14
【问题描述】:
我创建了这段代码来在 python 中找到 2 条线段之间的交点,但它似乎并没有为所有线产生正确的结果:
注意:我在游戏中使用它,其中 y 值会随着您的下降而增加。所以左上角是(0,0),左下角是(0,300)。不确定这是否会有所不同。
def getIntersectPoint(p1, p2, p3, p4):
e = sys.float_info.epsilon * 1000
# reorganize points from smaller to bigger in x-axis
if p2[0]<p1[0]:
p1,p2=p2,p1
if p4[0]<p3[0]:
p3,p4=p4,p3
rise1 = float(p2[1]-p1[1])
run1 = float(p2[0]-p1[0])
if abs(run1) <= e:
m1 = None
b1 = float(p1[0])
else:
m1 = rise1/run1
b1 = float(p1[1]-m1*p1[0])
rise2 = float(p4[1]-p3[1])
run2 = float(p4[0]-p3[0])
if abs(run2) <= e:
m2 = None
b2 = float(p3[0])
else:
m2 = rise2/run2
b2 = float(p3[1]-m2*p3[0])
# check if lines are parallel
if (m1==None and m2==None) or (m1!=None and m2!=None and abs(m1-m2)<=e):
#check if they are right on top of each other
if abs(b1-b2)<=e:
return () # infinite points
return None
elif m1==None:
iy2 = m2*b1 + b2
ix, iy = b1, iy2
elif m2==None:
iy1 = m1*b2 + b1
ix, iy = b2, iy1
else:
ix = (b1-b2)/(m2-m1)
iy = m1*ix + b1
# check if the intersection is in the bounding box
if ix>=p1[0]-e and ix<=p2[0]+e and ix>=p3[0]-e and ix<=p4[0]+e:
if iy>=p1[1]-e and iy<=p2[1]+e and iy>=p3[1]-e and iy<=p4[1]+e:
return [ix, iy]
return None
在p1,p2,p3,p4格式中找不到交集时生成的一些测试用例:
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [440, 0]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 0] [0, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [0, 280] [440, 280]
[-545.901858671, 443.161842698] [198.177615767, 149.315393477] [440, 0] [440, 280]
有谁知道怎么回事?
谢谢
【问题讨论】:
-
这无疑是一种测试线相交的创造性方法;我建议使用谷歌搜索更标准的线交叉点方法,并以此构建您的解决方案。
-
一些代码 cmets、测试用例和预期/失败输出会很有用
-
好的,我添加了一些失败的案例。
-
在this question的回答中给出了一个很好的方法。