赞
踩
- #!/usr/bin/python
- #-*- coding: UTF-8 -*-
- #
- # pip.py
- # point in polygon
- #
- # 2016-01-07
- #
- # point(pt) is inside polygon(poly)
- ########################################################################
-
- # gets extent of vertices vl
- #
- def extent_vertices(vl):
- min_x = 0.0
- min_y = 0.0
- max_x = 0.0
- max_y = 0.0
-
- i = 0
-
- for (x, y) in vl:
- if not i:
- (min_x, min_y) = (x, y)
- (max_x, max_y) = (x, y)
- i = 1
- else:
- if x < min_x:
- min_x = x
- if y < min_y:
- min_y = y
- if x > max_x:
- max_x = x
- if y > max_y:
- max_y = y
-
- return (min_x, min_y, max_x, max_y)
-
-
- # points p, q are on the same of line l
- #
- def same_side(l_start, l_end, p, q):
- dx, dy = float(l_end[0] - l_start[0]), float(l_end[1] - l_start[1])
- dx1, dy1 = float(p[0] - l_start[0]), float(p[1] - l_start[1])
- dx2, dy2 = float(q[0] - l_end[0]), float(q[1] - l_end[1])
-
- d = (dx * dy1 - dy * dx1) * (dx * dy2 - dy * dx2)
-
- if d >= 0:
- return 1
- else:
- return 0
-
-
- # are line segments s1, s2 intersect ?
- #
- def intersect_segs(s1_start, s1_end, s2_start, s2_end):
- if not same_side(s1_start, s1_end, s2_start, s2_end) and not same_side(s2_start, s2_end, s1_start, s1_end):
- return 1
- else:
- return 0
-
-
- # is point pt(x, y) in polygon poly
- # returns:
- # 0 : not in
- # 1 : in
- def pt_in_poly(pt, poly):
- np = len(poly)
- if np < 3:
- return 0
-
- (x, y) = pt
- (min_x, min_y, max_x, max_y) = extent_vertices(poly)
-
- if x < min_x or x > max_x or y < min_y or y > max_y:
- return 0
-
- # set a horizontal beam line (pt, w) from pt to the ultra right
- w = (max_x + max_x*0.1 + 1, y)
-
- c = 0
-
- for i in range(0, np):
- j = (i+1) % np
-
- if pt == poly[i]:
- return 1
- elif intersect_segs(poly[i], poly[j], pt, w):
- c = c + 1
- elif poly[i][1] == w[1]:
- k1 = (np + i - 1) % np
- while (k1 != i and poly[k1][1] == w[1]):
- k1 = (np + k1 - 1) % np
-
- k2 = (i+1) % np
- while (k2 != i and poly[k2][1] == w[1]):
- k2 = (k2 + 1) % np
-
- if k1 != k2 and not same_side(pt, w, poly[k1], poly[k2]):
- c = c + 1
-
- if k2 <= i:
- break
-
- i = k2
-
- return c % 2
-
- epsilon = 0.0000001
-
- assert pt_in_poly((0, 0), [(-1, -1), (-1, 1), (1, 1), (1, -1)]) == 1, "(1) appliaction error"
- assert pt_in_poly((-1, -1), [(-1, -1), (-1, 1), (1, 1), (1, -1)]) == 1, "(2) appliaction error"
- assert pt_in_poly((-1, 1), [(-1, -1), (-1, 1), (1, 1), (1, -1)]) == 1, "(3) appliaction error"
- assert pt_in_poly((-1 - epsilon, -1), [(-1, -1), (-1, 1), (1, 1), (1, -1)]) == 0, "(4) appliaction error"
- assert pt_in_poly((-1 + epsilon, -1 + epsilon), [(-1, -1), (-1, 1), (1, 1), (1, -1)]) == 1, "(5) appliaction error"
- assert pt_in_poly((-1 + epsilon, -1 + epsilon), [(-1, -1), (-1, 1), (1, 1), (1, -1)]) == 1, "(6) appliaction error"
- assert pt_in_poly((0, 0), [(-1, -1), (-1, 1), (1, 1), (1, 0), (2, -1)]) == 1, "(7) appliaction error"
- assert pt_in_poly((0, 0), [(-1, -1), (-1, 1), (1, 1), (1, 0), (2, 1), (2, -1)]) == 1, "(8) appliaction error"
- assert pt_in_poly((0, 0), [(-1, -1), (-1, 1), (1, 1), (1, 0), (2, 1), (2, 0), (2, -1)]) == 1, "(9) appliaction error"
- assert pt_in_poly((0, 0), [(-1, -1), (-1, 1), (1, 1), (1, 0), (2, 0), (3, 0), (2, -1)]) == 1, "(10) appliaction error"
- assert pt_in_poly((-2, 0), [(-1, -1), (-1, 1), (1, 1), (1, 0), (2, 0), (3, 0), (2, -1)]) == 0, "(11) appliaction error"
- assert pt_in_poly((3, 0), [(-1, -1), (-1, 1), (1, 1), (1, 0), (2, 0), (3, 0), (2, -1)]) == 1, "(12) appliaction error"

Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。