Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
sagemath
GitHub Repository: sagemath/sagesmc
Path: blob/master/src/sage/geometry/polyhedron/face.py
8817 views
1
"""
2
A class to keep information about faces of a polyhedron
3
4
This module gives you a tool to work with the faces of a polyhedron
5
and their relative position. First, you need to find the faces. To get
6
the faces in a particular dimension, use the
7
:meth:`~sage.geometry.poylhedron.base.face` method::
8
9
sage: P = polytopes.cross_polytope(3)
10
sage: P.faces(3)
11
(<0,1,2,3,4,5>,)
12
sage: P.faces(2)
13
(<0,1,2>, <0,1,3>, <0,2,4>, <0,3,4>, <3,4,5>, <2,4,5>, <1,3,5>, <1,2,5>)
14
sage: P.faces(1)
15
(<0,1>, <0,2>, <1,2>, <0,3>, <1,3>, <0,4>, <2,4>, <3,4>, <2,5>, <3,5>, <4,5>, <1,5>)
16
17
or :meth:`~sage.geometry.poylhedron.base.face_lattice` to get the
18
whole face lattice as a poset::
19
20
sage: P.face_lattice()
21
Finite poset containing 28 elements
22
23
The faces are printed in shorthand notation where each integer is the
24
index of a vertex/ray/line in the same order as the containing
25
Polyhedron's :meth:`~sage.geometry.polyhedron.base.Vrepresentation` ::
26
27
sage: face = P.faces(1)[3]; face
28
<0,3>
29
sage: P.Vrepresentation(0)
30
A vertex at (-1, 0, 0)
31
sage: P.Vrepresentation(3)
32
A vertex at (0, 0, 1)
33
sage: face.vertices()
34
(A vertex at (-1, 0, 0), A vertex at (0, 0, 1))
35
36
The face itself is not represented by Sage's
37
:func:`sage.geometry.polyhedron.constructor.Polyhedron` class, but by
38
an auxiliary class to keep the information. You can get the face as a
39
polyhedron with the :meth:`PolyhedronFace.as_polyhedron` method::
40
41
sage: face.as_polyhedron()
42
A 1-dimensional polyhedron in ZZ^3 defined as the convex hull of 2 vertices
43
sage: _.equations()
44
(An equation (0, 1, 0) x + 0 == 0,
45
An equation (1, 0, -1) x + 1 == 0)
46
"""
47
48
########################################################################
49
# Copyright (C) 2012 Volker Braun <[email protected]>
50
#
51
# Distributed under the terms of the GNU General Public License (GPL)
52
#
53
# http://www.gnu.org/licenses/
54
########################################################################
55
56
57
from sage.structure.sage_object import SageObject
58
from sage.misc.all import cached_method
59
from sage.modules.free_module_element import vector
60
from sage.matrix.constructor import matrix
61
62
63
64
#########################################################################
65
class PolyhedronFace(SageObject):
66
r"""
67
A face of a polyhedron.
68
69
This class is for use in
70
:meth:`~sage.geometry.polyhedron.base.Polyhedron_base.face_lattice`.
71
72
INPUT:
73
74
No checking is performed whether the H/V-representation indices
75
actually determine a face of the polyhedron. You should not
76
manually create :class:`PolyhedronFace` objects unless you know
77
what you are doing.
78
79
OUTPUT:
80
81
A :class:`PolyhedronFace`.
82
83
EXAMPLES::
84
85
sage: octahedron = polytopes.cross_polytope(3)
86
sage: inequality = octahedron.Hrepresentation(2)
87
sage: face_h = tuple([ inequality ])
88
sage: face_v = tuple( inequality.incident() )
89
sage: face_h_indices = [ h.index() for h in face_h ]
90
sage: face_v_indices = [ v.index() for v in face_v ]
91
sage: from sage.geometry.polyhedron.face import PolyhedronFace
92
sage: face = PolyhedronFace(octahedron, face_v_indices, face_h_indices)
93
sage: face
94
<0,1,2>
95
sage: face.dim()
96
2
97
sage: face.ambient_Hrepresentation()
98
(An inequality (1, 1, 1) x + 1 >= 0,)
99
sage: face.ambient_Vrepresentation()
100
(A vertex at (-1, 0, 0), A vertex at (0, -1, 0), A vertex at (0, 0, -1))
101
"""
102
103
def __init__(self, polyhedron, V_indices, H_indices):
104
r"""
105
The constructor.
106
107
See :class:`PolyhedronFace` for more information.
108
109
INPUT:
110
111
- ``polyhedron`` -- a :class:`Polyhedron`. The ambient
112
polyhedron.
113
114
- ``V_indices`` -- list of sorted integers. The indices of the
115
face-spanning V-representation objects in the ambient
116
polyhedron.
117
118
- ``H_indices`` -- list of sorted integers. The indices of the
119
H-representation objects of the ambient polyhedron that are
120
saturated on the face.
121
122
TESTS::
123
124
sage: from sage.geometry.polyhedron.face import PolyhedronFace
125
sage: PolyhedronFace(Polyhedron(), [], []) # indirect doctest
126
<>
127
"""
128
self._polyhedron = polyhedron
129
self._ambient_Vrepresentation_indices = tuple(V_indices)
130
self._ambient_Hrepresentation_indices = tuple(H_indices)
131
self._ambient_Vrepresentation = tuple( polyhedron.Vrepresentation(i) for i in V_indices )
132
self._ambient_Hrepresentation = tuple( polyhedron.Hrepresentation(i) for i in H_indices )
133
134
def vertex_generator(self):
135
"""
136
Return a generator for the vertices of the face.
137
138
EXAMPLES::
139
140
sage: triangle = Polyhedron(vertices=[[1,0],[0,1],[1,1]])
141
sage: face = triangle.faces(1)[0]
142
sage: for v in face.vertex_generator(): print(v)
143
A vertex at (0, 1)
144
A vertex at (1, 0)
145
sage: type(face.vertex_generator())
146
<type 'generator'>
147
"""
148
for V in self.ambient_Vrepresentation():
149
if V.is_vertex():
150
yield V
151
152
@cached_method
153
def vertices(self):
154
"""
155
Return all vertices of the face.
156
157
OUTPUT:
158
159
A tuple of vertices.
160
161
EXAMPLES::
162
163
sage: triangle = Polyhedron(vertices=[[1,0],[0,1],[1,1]])
164
sage: face = triangle.faces(1)[0]
165
sage: face.vertices()
166
(A vertex at (0, 1), A vertex at (1, 0))
167
"""
168
return tuple(self.vertex_generator())
169
170
def ray_generator(self):
171
"""
172
Return a generator for the rays of the face.
173
174
EXAMPLES::
175
176
sage: pi = Polyhedron(ieqs = [[1,1,0],[1,0,1]])
177
sage: face = pi.faces(1)[0]
178
sage: face.ray_generator().next()
179
A ray in the direction (1, 0)
180
"""
181
for V in self.ambient_Vrepresentation():
182
if V.is_ray():
183
yield V
184
185
@cached_method
186
def rays(self):
187
"""
188
Return the rays of the face.
189
190
OUTPUT:
191
192
A tuple of rays.
193
194
EXAMPLES::
195
196
sage: p = Polyhedron(ieqs = [[0,0,0,1],[0,0,1,0],[1,1,0,0]])
197
sage: face = p.faces(2)[0]
198
sage: face.rays()
199
(A ray in the direction (1, 0, 0), A ray in the direction (0, 1, 0))
200
"""
201
return tuple(self.ray_generator())
202
203
def line_generator(self):
204
"""
205
Return a generator for the lines of the face.
206
207
EXAMPLES::
208
209
sage: pr = Polyhedron(rays = [[1,0],[-1,0],[0,1]], vertices = [[-1,-1]])
210
sage: face = pr.faces(1)[0]
211
sage: face.line_generator().next()
212
A line in the direction (1, 0)
213
"""
214
for V in self.ambient_Vrepresentation():
215
if V.is_line():
216
yield V
217
218
@cached_method
219
def lines(self):
220
"""
221
Return all lines of the face.
222
223
OUTPUT:
224
225
A tuple of lines.
226
227
EXAMPLES::
228
229
sage: p = Polyhedron(rays = [[1,0],[-1,0],[0,1],[1,1]], vertices = [[-2,-2],[2,3]])
230
sage: p.lines()
231
(A line in the direction (1, 0),)
232
"""
233
return tuple(self.line_generator())
234
235
def __cmp__(self, other):
236
"""
237
Compare ``self`` and ``other``.
238
239
INPUT:
240
241
- ``other`` -- anything.
242
243
OUTPUT:
244
245
Two faces test equal if and only if they are faces of the same
246
(not just isomorphic) polyhedron and their generators have the
247
same indices.
248
249
EXAMPLES::
250
251
sage: square = polytopes.n_cube(2)
252
sage: f = square.faces(1)
253
sage: matrix(4,4, lambda i,j: cmp(f[i], f[j]))
254
[ 0 -1 -1 -1]
255
[ 1 0 -1 -1]
256
[ 1 1 0 -1]
257
[ 1 1 1 0]
258
"""
259
if not isinstance(other, PolyhedronFace):
260
return -1
261
if self._polyhedron is not other._polyhedron:
262
return -1
263
return cmp(self._ambient_Vrepresentation_indices,
264
other._ambient_Vrepresentation_indices)
265
266
def ambient_Hrepresentation(self, index=None):
267
r"""
268
Return the H-representation objects of the ambient polytope
269
defining the face.
270
271
INPUT:
272
273
- ``index`` -- optional. Either an integer or ``None``
274
(default).
275
276
OUTPUT:
277
278
If the optional argument is not present, a tuple of
279
H-representation objects. Each entry is either an inequality
280
or an equation.
281
282
If the optional integer ``index`` is specified, the
283
``index``-th element of the tuple is returned.
284
285
EXAMPLES::
286
287
sage: square = polytopes.n_cube(2)
288
sage: for face in square.face_lattice():
289
... print face.ambient_Hrepresentation()
290
(An inequality (1, 0) x + 1 >= 0, An inequality (0, 1) x + 1 >= 0,
291
An inequality (-1, 0) x + 1 >= 0, An inequality (0, -1) x + 1 >= 0)
292
(An inequality (1, 0) x + 1 >= 0, An inequality (0, 1) x + 1 >= 0)
293
(An inequality (1, 0) x + 1 >= 0, An inequality (0, -1) x + 1 >= 0)
294
(An inequality (0, 1) x + 1 >= 0, An inequality (-1, 0) x + 1 >= 0)
295
(An inequality (-1, 0) x + 1 >= 0, An inequality (0, -1) x + 1 >= 0)
296
(An inequality (1, 0) x + 1 >= 0,)
297
(An inequality (0, 1) x + 1 >= 0,)
298
(An inequality (-1, 0) x + 1 >= 0,)
299
(An inequality (0, -1) x + 1 >= 0,)
300
()
301
"""
302
if index==None:
303
return self._ambient_Hrepresentation
304
else:
305
return self._ambient_Hrepresentation[index]
306
307
def ambient_Vrepresentation(self, index=None):
308
r"""
309
Return the V-representation objects of the ambient polytope
310
defining the face.
311
312
INPUT:
313
314
- ``index`` -- optional. Either an integer or ``None``
315
(default).
316
317
OUTPUT:
318
319
If the optional argument is not present, a tuple of
320
V-representation objects. Each entry is either a vertex, a
321
ray, or a line.
322
323
If the optional integer ``index`` is specified, the
324
``index``-th element of the tuple is returned.
325
326
EXAMPLES::
327
328
sage: square = polytopes.n_cube(2)
329
sage: for fl in square.face_lattice():
330
... print fl.ambient_Vrepresentation()
331
...
332
()
333
(A vertex at (-1, -1),)
334
(A vertex at (-1, 1),)
335
(A vertex at (1, -1),)
336
(A vertex at (1, 1),)
337
(A vertex at (-1, -1), A vertex at (-1, 1))
338
(A vertex at (-1, -1), A vertex at (1, -1))
339
(A vertex at (1, -1), A vertex at (1, 1))
340
(A vertex at (-1, 1), A vertex at (1, 1))
341
(A vertex at (-1, -1), A vertex at (-1, 1),
342
A vertex at (1, -1), A vertex at (1, 1))
343
"""
344
if index==None:
345
return self._ambient_Vrepresentation
346
else:
347
return self._ambient_Vrepresentation[index]
348
349
def n_ambient_Hrepresentation(self):
350
"""
351
Return the number of objects that make up the ambient
352
H-representation of the polyhedron.
353
354
See also :meth:`ambient_Hrepresentation`.
355
356
OUTPUT:
357
358
Integer.
359
360
EXAMPLES::
361
362
sage: p = polytopes.cross_polytope(4)
363
sage: face = p.face_lattice()[10]
364
sage: face
365
<0,2>
366
sage: face.ambient_Hrepresentation()
367
(An inequality (1, -1, 1, -1) x + 1 >= 0,
368
An inequality (1, 1, 1, 1) x + 1 >= 0,
369
An inequality (1, 1, 1, -1) x + 1 >= 0,
370
An inequality (1, -1, 1, 1) x + 1 >= 0)
371
sage: face.n_ambient_Hrepresentation()
372
4
373
"""
374
return len(self.ambient_Hrepresentation())
375
376
def n_ambient_Vrepresentation(self):
377
"""
378
Return the number of objects that make up the ambient
379
V-representation of the polyhedron.
380
381
See also :meth:`ambient_Vrepresentation`.
382
383
OUTPUT:
384
385
Integer.
386
387
EXAMPLES::
388
389
sage: p = polytopes.cross_polytope(4)
390
sage: face = p.face_lattice()[10]
391
sage: face
392
<0,2>
393
sage: face.ambient_Vrepresentation()
394
(A vertex at (-1, 0, 0, 0), A vertex at (0, 0, -1, 0))
395
sage: face.n_ambient_Vrepresentation()
396
2
397
"""
398
return len(self.ambient_Vrepresentation())
399
400
def ambient_dim(self):
401
r"""
402
Return the dimension of the containing polyhedron.
403
404
EXAMPLES::
405
406
sage: P = Polyhedron(vertices = [[1,0,0,0],[0,1,0,0]])
407
sage: face = P.faces(1)[0]
408
sage: face.ambient_dim()
409
4
410
"""
411
return self._polyhedron.ambient_dim()
412
413
@cached_method
414
def dim(self):
415
"""
416
Return the dimension of the face.
417
418
OUTPUT:
419
420
Integer.
421
422
EXAMPLES::
423
424
sage: fl = polytopes.dodecahedron().face_lattice()
425
sage: [ x.dim() for x in fl ]
426
[-1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
427
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
428
1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 3]
429
"""
430
if self.n_ambient_Vrepresentation()==0:
431
return -1
432
else:
433
origin = vector(self.ambient_Vrepresentation(0))
434
v_list = [ vector(v)-origin for v in self.ambient_Vrepresentation() ]
435
return matrix(v_list).rank()
436
437
def _repr_(self):
438
r"""
439
Return a string representation.
440
441
OUTPUT:
442
443
A string listing the V-representation indices of the face.
444
445
EXAMPLES::
446
447
sage: square = polytopes.n_cube(2)
448
sage: a_face = list( square.face_lattice() )[8]
449
sage: a_face.__repr__()
450
'<1,3>'
451
"""
452
s = '<'
453
s += ','.join([ str(v.index()) for v in self.ambient_Vrepresentation() ])
454
s += '>'
455
return s
456
457
def polyhedron(self):
458
"""
459
Return the containing polyhedron.
460
461
EXAMPLES::
462
463
sage: P = polytopes.cross_polytope(3); P
464
A 3-dimensional polyhedron in ZZ^3 defined as the convex hull of 6 vertices
465
sage: face = P.faces(2)[3]
466
sage: face
467
<0,3,4>
468
sage: face.polyhedron()
469
A 3-dimensional polyhedron in ZZ^3 defined as the convex hull of 6 vertices
470
"""
471
return self._polyhedron
472
473
@cached_method
474
def as_polyhedron(self):
475
"""
476
Return the face as an independent polyhedron.
477
478
OUTPUT:
479
480
A polyhedron.
481
482
EXAMPLES::
483
484
sage: P = polytopes.cross_polytope(3); P
485
A 3-dimensional polyhedron in ZZ^3 defined as the convex hull of 6 vertices
486
sage: face = P.faces(2)[3]
487
sage: face
488
<0,3,4>
489
sage: face.as_polyhedron()
490
A 2-dimensional polyhedron in ZZ^3 defined as the convex hull of 3 vertices
491
492
sage: P.intersection(face.as_polyhedron()) == face.as_polyhedron()
493
True
494
"""
495
P = self._polyhedron
496
parent = P.parent()
497
Vrep = (self.vertices(), self.rays(), self.lines())
498
return P.__class__(parent, Vrep, None)
499
500