- sage: set_random_seed()
- sage: K = random_cone(max_ambient_dim=4)
- sage: pi_of_K = positive_operator_gens(K)
- sage: L = ToricLattice(K.lattice_dim()**2)
- sage: pi_cone = Cone([p.list() for p in pi_of_K],
- ....: lattice=L,
- ....: check=False)
- sage: K.is_proper() == pi_cone.is_proper()
- True
- """
- # Matrices are not vectors in Sage, so we have to convert them
- # to vectors explicitly before we can find a basis. We need these
- # two values to construct the appropriate "long vector" space.
- F = K.lattice().base_field()
- n = K.lattice_dim()
-
- tensor_products = [ s.tensor_product(x) for x in K for s in K.dual() ]
-
- # Convert those tensor products to long vectors.
- W = VectorSpace(F, n**2)
- vectors = [ W(tp.list()) for tp in tensor_products ]
-
- check = True
- if K.is_solid() or K.is_strictly_convex():
- # The lineality space of either ``K`` or ``K.dual()`` is
- # trivial and it's easy to show that our generating set is
- # minimal. I would love a proof that this works when ``K`` is
- # neither pointed nor solid.
- #
- # Note that in that case we can get *duplicates*, since the
- # tensor product of (x,s) is the same as that of (-x,-s).
- check = False
-
- # Create the dual cone of the positive operators, expressed as
- # long vectors.
- pi_dual = Cone(vectors, ToricLattice(W.dimension()), check=check)
-
- # Now compute the desired cone from its dual...
- pi_cone = pi_dual.dual()
-
- # And finally convert its rays back to matrix representations.
- M = MatrixSpace(F, n)
- return [ M(v.list()) for v in pi_cone ]
-
-
-def Z_transformation_gens(K):
- r"""
- Compute generators of the cone of Z-transformations on this cone.