|
jbronn@138
|
1 |
import unittest |
|
jbronn@138
|
2 |
from pymutable_geometries import * |
|
jbronn@138
|
3 |
from django.contrib.gis.geos.error import GEOSIndexError |
|
jbronn@138
|
4 |
|
|
jbronn@138
|
5 |
class GEOSPyMutableTest(unittest.TestCase): |
|
jbronn@138
|
6 |
''' |
|
jbronn@138
|
7 |
Tests Pythonic Mutability of Python GEOS geometry wrappers |
|
jbronn@138
|
8 |
get/set/delitem on a slice, normal list methods |
|
jbronn@138
|
9 |
''' |
|
jbronn@138
|
10 |
|
|
jbronn@138
|
11 |
def test01_getitem(self): |
|
jbronn@138
|
12 |
'Test getting a single item from a geometry' |
|
jbronn@138
|
13 |
for g in slice_geometries(): |
|
jbronn@138
|
14 |
for i in seqrange(): |
|
jbronn@138
|
15 |
self.assertEqual(g.coords[i], getcoords(g.geom[i])) |
|
jbronn@138
|
16 |
|
|
jbronn@138
|
17 |
def test02_getslice(self): |
|
jbronn@138
|
18 |
'Test getting a slice from a geometry' |
|
jbronn@138
|
19 |
for f in getslice_functions(): |
|
jbronn@138
|
20 |
for g in slice_geometries(): |
|
jbronn@138
|
21 |
msg = "fcn %s, geom %s" % (f.__name__, str(g.geom_type)) |
|
jbronn@138
|
22 |
self.assertEqual(f(g.coords), getcoords(f(g.geom)), msg) |
|
jbronn@138
|
23 |
|
|
jbronn@138
|
24 |
def test03_getitem_indexException(self): |
|
jbronn@138
|
25 |
'Test get single item with out-of-bounds index' |
|
jbronn@138
|
26 |
for g in slice_geometries(): |
|
jbronn@138
|
27 |
for i in SEQ_OUT_OF_BOUNDS: |
|
jbronn@138
|
28 |
self.assertRaises(GEOSIndexError, lambda: g.geom[i]) |
|
jbronn@138
|
29 |
|
|
jbronn@138
|
30 |
def test04_delitem_single(self): |
|
jbronn@138
|
31 |
'Test delete single item from a geometry' |
|
jbronn@138
|
32 |
for i in seqrange(): |
|
jbronn@138
|
33 |
for g in slice_geometries(): |
|
jbronn@138
|
34 |
if g.geom.ring and i in SEQ_BOUNDS: continue |
|
jbronn@138
|
35 |
del g.coords[i] |
|
jbronn@138
|
36 |
del g.geom[i] |
|
jbronn@138
|
37 |
self.assertEqual(g.tuple_coords, g.geom.coords) |
|
jbronn@138
|
38 |
|
|
jbronn@138
|
39 |
def test05_delitem_slice(self): |
|
jbronn@138
|
40 |
'Test delete slice from a geometry' |
|
jbronn@138
|
41 |
for f in delslice_functions(): |
|
jbronn@138
|
42 |
for g in slice_geometries(): |
|
jbronn@138
|
43 |
if g.geom.ring and not f.ring: continue |
|
jbronn@138
|
44 |
f(g.coords) |
|
jbronn@138
|
45 |
f(g.geom) |
|
jbronn@138
|
46 |
msg = "fcn %s, geom %s" % (f.__name__, str(g.geom_type)) |
|
jbronn@138
|
47 |
self.assertEqual(g.tuple_coords, g.geom.coords, msg) |
|
jbronn@138
|
48 |
|
|
jbronn@138
|
49 |
def test06_delitem_single_indexException(self): |
|
jbronn@138
|
50 |
'Test delete single item with out-of-bounds index' |
|
jbronn@138
|
51 |
def func(x, i): del x[i] |
|
jbronn@138
|
52 |
for g in slice_geometries(): |
|
jbronn@138
|
53 |
for i in SEQ_OUT_OF_BOUNDS: |
|
jbronn@138
|
54 |
self.assertRaises(GEOSIndexError, func, g.geom, i) |
|
jbronn@138
|
55 |
|
|
jbronn@138
|
56 |
def test07_setitem_single(self): |
|
jbronn@138
|
57 |
"Test set single item (make sure we didn't break this)" |
|
jbronn@138
|
58 |
for i in seqrange(): |
|
jbronn@138
|
59 |
for g in slice_geometries(): |
|
jbronn@138
|
60 |
if g.geom.ring and i in SEQ_BOUNDS: continue |
|
jbronn@138
|
61 |
ag, ac = g.newitem(rng=(400,410)) |
|
jbronn@138
|
62 |
g.coords[i] = ac |
|
jbronn@138
|
63 |
g.geom[i] = ag |
|
jbronn@138
|
64 |
self.assertEqual(g.tuple_coords, g.geom.coords) |
|
jbronn@138
|
65 |
|
|
jbronn@138
|
66 |
def test08_setslice_simple(self): |
|
jbronn@138
|
67 |
'Test setting a simple slice of a geometry' |
|
jbronn@138
|
68 |
for g in slice_geometries(): |
|
jbronn@138
|
69 |
for f in setslice_simple_functions(g): |
|
jbronn@138
|
70 |
if g.geom.ring and not f.ring: continue |
|
jbronn@138
|
71 |
f(g.coords) |
|
jbronn@138
|
72 |
f(g.geom) |
|
jbronn@138
|
73 |
msg = "fcn %s, geom %s" % (f.__name__, str(g.geom_type)) |
|
jbronn@138
|
74 |
self.assertEqual(g.tuple_coords, g.geom.coords, msg) |
|
jbronn@138
|
75 |
|
|
jbronn@138
|
76 |
def test09_setslice_extended(self): |
|
jbronn@138
|
77 |
'Test setting an extended slice of a geometry' |
|
jbronn@138
|
78 |
for g in slice_geometries(): |
|
jbronn@138
|
79 |
for f in setslice_extended_functions(g): |
|
jbronn@138
|
80 |
if g.geom.ring and not f.ring: continue |
|
jbronn@138
|
81 |
f(g.coords) |
|
jbronn@138
|
82 |
f(g.geom) |
|
jbronn@138
|
83 |
msg = "fcn %s, geom %s" % (f.__name__, str(g.geom_type)) |
|
jbronn@138
|
84 |
self.assertEqual(g.tuple_coords, g.geom.coords, msg) |
|
jbronn@138
|
85 |
|
|
jbronn@138
|
86 |
def test10_setslice_extended_mismatched(self): |
|
jbronn@138
|
87 |
'Test setting extended slice with array of mismatched length' |
|
jbronn@138
|
88 |
for g in slice_geometries(): |
|
jbronn@138
|
89 |
ag, ac = g.newitem(rng=(400,410)) |
|
jbronn@138
|
90 |
def func(): g.geom[2:8:2] = [ ag, ] |
|
jbronn@138
|
91 |
self.assertRaises(ValueError, func) |
|
jbronn@138
|
92 |
|
|
jbronn@138
|
93 |
def test11_setitem_single_indexException(self): |
|
jbronn@138
|
94 |
'Test set single item with out-of-bounds index' |
|
jbronn@138
|
95 |
for g in slice_geometries(): |
|
jbronn@138
|
96 |
ag, ac = g.newitem(rng=(400,410)) |
|
jbronn@138
|
97 |
def func(i): g.geom[i] = ag |
|
jbronn@138
|
98 |
for i in SEQ_OUT_OF_BOUNDS: |
|
jbronn@138
|
99 |
self.assertRaises(GEOSIndexError, func, i) |
|
jbronn@138
|
100 |
|
|
jbronn@138
|
101 |
def test12_append(self): |
|
jbronn@138
|
102 |
'Test list method append' |
|
jbronn@138
|
103 |
for g in slice_geometries(ring=False): |
|
jbronn@138
|
104 |
ag, ac = g.newitem(rng=(400,410)) |
|
jbronn@138
|
105 |
g.geom.append(ag) |
|
jbronn@138
|
106 |
g.coords.append(ac) |
|
jbronn@138
|
107 |
self.assertEqual(g.tuple_coords, g.geom.coords) |
|
jbronn@138
|
108 |
|
|
jbronn@138
|
109 |
def test13_extend(self): |
|
jbronn@138
|
110 |
'Test list method extend' |
|
jbronn@138
|
111 |
for g in slice_geometries(): |
|
jbronn@138
|
112 |
items = g.coords_fcn(5) |
|
jbronn@138
|
113 |
if g.geom.ring: items[-1] = g.coords[0] |
|
jbronn@138
|
114 |
g.geom.extend(map(g.subtype,items)) |
|
jbronn@138
|
115 |
g.coords.extend(items) |
|
jbronn@138
|
116 |
self.assertEqual(g.tuple_coords, g.geom.coords) |
|
jbronn@138
|
117 |
|
|
jbronn@138
|
118 |
def test14_insert(self): |
|
jbronn@138
|
119 |
'Test list method insert' |
|
jbronn@138
|
120 |
for i in xrange(*SEQ_OUT_OF_BOUNDS): |
|
jbronn@138
|
121 |
for g in slice_geometries(): |
|
jbronn@138
|
122 |
if g.geom.ring and i in SEQ_BOUNDS + SEQ_OUT_OF_BOUNDS: |
|
jbronn@138
|
123 |
continue |
|
jbronn@138
|
124 |
ag, ac = g.newitem(rng=(200,250)) |
|
jbronn@138
|
125 |
g.geom.insert(i, ag) |
|
jbronn@138
|
126 |
g.coords.insert(i, ac) |
|
jbronn@138
|
127 |
self.assertEqual(g.tuple_coords, g.geom.coords) |
|
jbronn@138
|
128 |
|
|
jbronn@138
|
129 |
def test15_insert_typeError(self): |
|
jbronn@138
|
130 |
'Test list method insert raises error on invalid index' |
|
jbronn@138
|
131 |
for g in slice_geometries(): |
|
jbronn@138
|
132 |
ag, ac = g.newitem(rng=(200,250)) |
|
jbronn@138
|
133 |
self.assertRaises(TypeError, g.geom.insert, 'hi', ag) |
|
jbronn@138
|
134 |
|
|
jbronn@138
|
135 |
def test16_pop(self): |
|
jbronn@138
|
136 |
'Test list method pop' |
|
jbronn@138
|
137 |
for i in seqrange(): |
|
jbronn@138
|
138 |
for g in slice_geometries(): |
|
jbronn@138
|
139 |
if g.geom.ring and i in SEQ_BOUNDS + SEQ_OUT_OF_BOUNDS: |
|
jbronn@138
|
140 |
continue |
|
jbronn@138
|
141 |
self.assertEqual(g.coords.pop(i), getcoords(g.geom.pop(i))) |
|
jbronn@138
|
142 |
|
|
jbronn@138
|
143 |
def test16_index(self): |
|
jbronn@138
|
144 |
'Test list method index' |
|
jbronn@138
|
145 |
for i in xrange(0, SEQ_LENGTH): |
|
jbronn@138
|
146 |
for g in slice_geometries(): |
|
jbronn@138
|
147 |
if g.geom.ring and i in SEQ_BOUNDS: continue |
|
jbronn@138
|
148 |
ag, ac = g.newitem(rng=(400,410)) |
|
jbronn@138
|
149 |
g.geom[i] = ag |
|
jbronn@138
|
150 |
self.assertEqual(i, g.geom.index(ag)) |
|
jbronn@138
|
151 |
|
|
jbronn@138
|
152 |
def test17_index_ValueError(self): |
|
jbronn@138
|
153 |
'Test list method raises ValueError if value not found' |
|
jbronn@138
|
154 |
for g in slice_geometries(): |
|
jbronn@138
|
155 |
ag, ac = g.newitem(rng=(400,410)) |
|
jbronn@138
|
156 |
self.assertRaises(ValueError, g.geom.index, ag) |
|
jbronn@138
|
157 |
|
|
jbronn@138
|
158 |
def test18_remove(self): |
|
jbronn@138
|
159 |
'Test list method remove' |
|
jbronn@138
|
160 |
for i in xrange(0, SEQ_LENGTH): |
|
jbronn@138
|
161 |
for g in slice_geometries(): |
|
jbronn@138
|
162 |
if g.geom.ring and i in SEQ_BOUNDS: continue |
|
jbronn@138
|
163 |
ag, ac = g.newitem(rng=(400,410)) |
|
jbronn@138
|
164 |
g.geom[i] = ag |
|
jbronn@138
|
165 |
g.coords[i] = ac |
|
jbronn@138
|
166 |
g.geom.remove(ag) |
|
jbronn@138
|
167 |
g.coords.remove(ac) |
|
jbronn@138
|
168 |
self.assertEqual(g.tuple_coords, g.geom.coords) |
|
jbronn@138
|
169 |
|
|
jbronn@138
|
170 |
def test19_count(self): |
|
jbronn@138
|
171 |
'Test list method count' |
|
jbronn@138
|
172 |
for g in slice_geometries(): |
|
jbronn@138
|
173 |
self.assertEqual(SEQ_LENGTH, g.geom.count()) |
|
jbronn@138
|
174 |
|
|
jbronn@138
|
175 |
def test20_setslice_geos_fcns(self): |
|
jbronn@138
|
176 |
'Test geos properties after setting a simple slice of a geometry' |
|
jbronn@138
|
177 |
for g in slice_geometries(ring=False): |
|
jbronn@138
|
178 |
for f in setslice_simple_functions(g): |
|
jbronn@138
|
179 |
f(g.coords) |
|
jbronn@138
|
180 |
f(g.geom) |
|
jbronn@138
|
181 |
if not len(g.coords): continue |
|
jbronn@138
|
182 |
for tf in test_geos_functions(): |
|
jbronn@138
|
183 |
cg = g.make_geom() |
|
jbronn@138
|
184 |
self.assertEqual(tf(cg) , tf(g.geom)) |
|
jbronn@138
|
185 |
|
|
jbronn@138
|
186 |
def test21_delslice_geos_fcns(self): |
|
jbronn@138
|
187 |
'Test geos properties after deleting a slice of a geometry' |
|
jbronn@138
|
188 |
for f in delslice_functions(): |
|
jbronn@138
|
189 |
for g in slice_geometries(ring=False): |
|
jbronn@138
|
190 |
f(g.coords) |
|
jbronn@138
|
191 |
f(g.geom) |
|
jbronn@138
|
192 |
if not len(g.coords): continue |
|
jbronn@138
|
193 |
for tf in test_geos_functions(): |
|
jbronn@138
|
194 |
cg = g.make_geom() |
|
jbronn@138
|
195 |
self.assertEqual(tf(cg) , tf(g.geom)) |
|
jbronn@138
|
196 |
|
|
jbronn@138
|
197 |
def suite(): |
|
jbronn@138
|
198 |
s = unittest.TestSuite() |
|
jbronn@138
|
199 |
s.addTest(unittest.makeSuite(GEOSPyMutableTest)) |
|
jbronn@138
|
200 |
return s |
|
jbronn@138
|
201 |
|
|
jbronn@138
|
202 |
def run(verbosity=2): |
|
jbronn@138
|
203 |
unittest.TextTestRunner(verbosity=verbosity).run(suite()) |
|
jbronn@138
|
204 |
|
|
jbronn@138
|
205 |
if __name__ == '__main__': |
|
jbronn@138
|
206 |
run() |