add epsilon to collinearity test, plus a demo
This commit is contained in:
parent
bb3b025ecd
commit
634ed47f42
1 changed files with 45 additions and 4 deletions
49
geometry.py
49
geometry.py
|
|
@ -4,6 +4,7 @@ from __future__ import division
|
||||||
import math
|
import math
|
||||||
|
|
||||||
epsilon = 1e-6
|
epsilon = 1e-6
|
||||||
|
# epsilon = 0
|
||||||
|
|
||||||
def x( point ):
|
def x( point ):
|
||||||
return point[0]
|
return point[0]
|
||||||
|
|
@ -49,14 +50,16 @@ def is_point( segment ):
|
||||||
return segment[0] == segment[1]
|
return segment[0] == segment[1]
|
||||||
|
|
||||||
|
|
||||||
def collinear( p, q, r ):
|
def collinear( p, q, r, e = epsilon ):
|
||||||
"""Returns True if the 3 given points are collinear.
|
"""Returns True if the 3 given points are collinear.
|
||||||
|
|
||||||
Note: there is a lot of algorithm to test collinearity, the most known involving linear algebra.
|
Note: there is a lot of algorithm to test collinearity, the most known involving linear algebra.
|
||||||
This one has been found in Jonathan Shewchuk's "Lecture Notes on Geometric Robustness".
|
This one has been found in Jonathan Shewchuk's "Lecture Notes on Geometric Robustness".
|
||||||
It is maybe the most elegant one: just arithmetic on x and y, without ifs, sqrt or risk of divide-by-zero error.
|
It is maybe the most elegant one: just arithmetic on x and y, without ifs, sqrt or risk of divide-by-zero error.
|
||||||
"""
|
"""
|
||||||
return (x(p)-x(r)) * (y(q)-y(r)) == (x(q)-x(r)) * (y(p)-y(r))
|
# Without epsilon comparison, this would ends as:
|
||||||
|
# return (x(p)-x(r)) * (y(q)-y(r)) == (x(q)-x(r)) * (y(p)-y(r))
|
||||||
|
return abs((x(p)-x(r)) * (y(q)-y(r)) - (x(q)-x(r)) * (y(p)-y(r))) <= e
|
||||||
|
|
||||||
|
|
||||||
def line_intersection( seg0, seg1 ):
|
def line_intersection( seg0, seg1 ):
|
||||||
|
|
@ -162,6 +165,7 @@ if __name__ == "__main__":
|
||||||
import uberplot
|
import uberplot
|
||||||
import matplotlib.pyplot as plot
|
import matplotlib.pyplot as plot
|
||||||
|
|
||||||
|
# intersections demo
|
||||||
if len(sys.argv) > 1:
|
if len(sys.argv) > 1:
|
||||||
scale = 100
|
scale = 100
|
||||||
nb = int(sys.argv[1])
|
nb = int(sys.argv[1])
|
||||||
|
|
@ -198,11 +202,48 @@ if __name__ == "__main__":
|
||||||
|
|
||||||
fig = plot.figure()
|
fig = plot.figure()
|
||||||
|
|
||||||
ax = fig.add_subplot(111)
|
ax = fig.add_subplot(121)
|
||||||
ax.set_aspect('equal')
|
|
||||||
uberplot.plot_segments( ax, segments, linewidth=0.5, edgecolor = "blue" )
|
uberplot.plot_segments( ax, segments, linewidth=0.5, edgecolor = "blue" )
|
||||||
uberplot.scatter_points( ax, points, edgecolor="blue", facecolor="blue", s=120, alpha=1, linewidth=1 )
|
uberplot.scatter_points( ax, points, edgecolor="blue", facecolor="blue", s=120, alpha=1, linewidth=1 )
|
||||||
uberplot.scatter_points( ax, line_inter, edgecolor="none", facecolor="green", s=60, alpha=0.5 )
|
uberplot.scatter_points( ax, line_inter, edgecolor="none", facecolor="green", s=60, alpha=0.5 )
|
||||||
uberplot.scatter_points( ax, seg_inter, edgecolor="none", facecolor="red", s=60, alpha=0.5 )
|
uberplot.scatter_points( ax, seg_inter, edgecolor="none", facecolor="red", s=60, alpha=0.5 )
|
||||||
|
ax.set_aspect('equal')
|
||||||
|
|
||||||
|
|
||||||
|
# collinear test demo
|
||||||
|
if len(sys.argv) > 1:
|
||||||
|
scale = 100
|
||||||
|
nb = int(sys.argv[1])
|
||||||
|
triangles = []
|
||||||
|
for t in range(nb):
|
||||||
|
triangles.append( [ [scale*random.random(),scale*random.random()] for i in range(3)] )
|
||||||
|
# forced collinear
|
||||||
|
t = [ [scale*random.random(),scale*random.random()] for i in range(2)]
|
||||||
|
triangles.append( [t[0],t[1],t[0]] )
|
||||||
|
|
||||||
|
else:
|
||||||
|
triangles = [
|
||||||
|
[(-60.45085, -24.898983), (-68.54102, -30.776835), (-58.54102, -30.776835)],
|
||||||
|
[(-68.54102, -0.0), (-65.45085, -9.510565), (-58.54102, -0.0)],
|
||||||
|
[(-65.45085, 9.510565), (-68.54102, -0.0), (-58.54102, -0.0)],
|
||||||
|
[(-68.54102, 30.776835), (-60.45085, 24.898983), (-58.54102, 30.776835)],
|
||||||
|
[(-58.54102, -0.0), (-65.45085, -9.510565), (-55.45085, -9.510565)],
|
||||||
|
[(-65.45085, -9.510565), (-57.36068, -15.388418), (-55.45085, -9.510565)],
|
||||||
|
[(-65.45085, 9.510565), (-58.54102, -0.0), (-55.45085, 9.510565)],
|
||||||
|
[(-65.45085, 9.510565), (-65.45085, 9.510565), (-55.45085, 9.510565)], # is collinear
|
||||||
|
]
|
||||||
|
|
||||||
|
ax = fig.add_subplot(122)
|
||||||
|
|
||||||
|
for triangle in triangles:
|
||||||
|
status="green"
|
||||||
|
if collinear(*triangle):
|
||||||
|
status="red"
|
||||||
|
uberplot.plot_segments( ax, utils.tour(triangle), edgecolor = status )
|
||||||
|
|
||||||
|
# ax.set_aspect('equal')
|
||||||
|
ax.axis('auto')
|
||||||
|
|
||||||
|
|
||||||
plot.show()
|
plot.show()
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue