Path: blob/master/src/sage/geometry/hyperplane_arrangement/library.py
8817 views
r"""1Library of Hyperplane Arrangements23A collection of useful or interesting hyperplane arrangements. See4:mod:`sage.geometry.hyperplane_arrangement.arrangement` for details5about how to construct your own hyperplane arrangements.6"""7#*****************************************************************************8# Copyright (C) 2013 David Perkinson <[email protected]>9#10# Distributed under the terms of the GNU General Public License (GPL)11# http://www.gnu.org/licenses/12#*****************************************************************************1314from sage.graphs.all import graphs15from sage.matrix.constructor import matrix, random_matrix16from sage.rings.all import QQ, ZZ17from sage.misc.misc_c import prod1819from sage.combinat.combinat import stirling_number220from sage.rings.arith import binomial21from sage.rings.polynomial.polynomial_ring import polygen2223from sage.geometry.hyperplane_arrangement.arrangement import HyperplaneArrangements242526def make_parent(base_ring, dimension, names=None):27"""28Construct the parent for the hyperplane arrangements.2930For internal use only.3132INPUT:3334- ``base_ring`` -- a ring3536- ``dimenison`` -- integer3738- ``names`` -- ``None`` (default) or a list/tuple/iterable of39strings4041OUTPUT:4243A new44:class:`~sage.geometry.hyperplane_arrangement.arrangement.HyperplaneArrangements`45instance.4647EXAMPLES::4849sage: from sage.geometry.hyperplane_arrangement.library import make_parent50sage: make_parent(QQ, 3)51Hyperplane arrangements in 3-dimensional linear space over52Rational Field with coordinates t0, t1, t253"""54if names is None:55names = tuple('t'+str(i) for i in range(dimension))56else:57names = tuple(map(str, names))58if len(names) != dimension:59raise ValueError('number of variable names does not match dimension')60return HyperplaneArrangements(base_ring, names=names)61626364class HyperplaneArrangementLibrary(object):65"""66The library of hyperplane arrangements.67"""6869def braid(self, n, K=QQ, names=None):70r"""71The braid arrangement.7273INPUT:7475- ``n`` -- integer7677- ``K`` -- field (default: ``QQ``)7879- ``names`` -- tuple of strings or ``None`` (default); the80variable names for the ambient space8182OUTPUT:8384The hyperplane arrangement consisting of the `n(n-1)/2`85hyperplanes `\{ x_i - x_j = 0 : 1 \leq i \leq j \leq n \}`.8687EXAMPLES::8889sage: hyperplane_arrangements.braid(4)90Arrangement of 6 hyperplanes of dimension 4 and rank 391"""92x = polygen(QQ, 'x')93A = self.graphical(graphs.CompleteGraph(n), K, names=names)94charpoly = prod(x-i for i in range(n))95A.characteristic_polynomial.set_cache(charpoly)96return A9798def bigraphical(self, G, A=None, K=QQ, names=None):99r"""100Return a bigraphical hyperplane arrangement.101102INPUT:103104- ``G`` -- graph105106- ``A`` -- list, matrix, dictionary (default: ``None``107gives semiorder), or the string 'generic'108109- ``K`` -- field (default: `\QQ`)110111- ``names`` -- tuple of strings or ``None`` (default); the112variable names for the ambient space113114OUTPUT:115116The hyperplane arrangement with hyperplanes `x_i - x_j =117A[i,j]` and `x_j - x_i = A[j,i]` for each edge `v_i, v_j` of118``G``. The indices `i,j` are the indices of elements of119``G.vertices()``.120121EXAMPLES::122123sage: G = graphs.CycleGraph(4)124sage: G.edges()125[(0, 1, None), (0, 3, None), (1, 2, None), (2, 3, None)]126sage: G.edges(labels=False)127[(0, 1), (0, 3), (1, 2), (2, 3)]128sage: A = {0:{1:1, 3:2}, 1:{0:3, 2:0}, 2:{1:2, 3:1}, 3:{2:0, 0:2}}129sage: HA = hyperplane_arrangements.bigraphical(G, A)130sage: HA.n_regions()13163132sage: hyperplane_arrangements.bigraphical(G, 'generic').n_regions()13365134sage: hyperplane_arrangements.bigraphical(G).n_regions()13559136137REFERENCES:138139.. [BigraphicalArrangements] S. Hopkins, D. Perkinson.140"Bigraphical Arrangements".141:arxiv:`1212.4398`142"""143n = G.num_verts()144if A is None: # default to G-semiorder arrangement145A = matrix(K, n, lambda i, j: 1)146elif A == 'generic':147A = random_matrix(ZZ, n, x=10000)148A = matrix(K, A)149H = make_parent(K, n, names)150x = H.gens()151hyperplanes = []152for e in G.edges():153i = G.vertices().index(e[0])154j = G.vertices().index(e[1])155hyperplanes.append( x[i] - x[j] - A[i][j])156hyperplanes.append(-x[i] + x[j] - A[j][i])157return H(*hyperplanes)158159def Catalan(self, n, K=QQ, names=None):160r"""161Return the Catalan arrangement.162163INPUT:164165- ``n`` -- integer166167- ``K`` -- field (default: `\QQ`)168169- ``names`` -- tuple of strings or ``None`` (default); the170variable names for the ambient space171172OUTPUT:173174The arrangement of `3n(n-1)/2` hyperplanes `\{ x_i - x_j =175-1,0,1 : 1 \leq i \leq j \leq n \}`.176177EXAMPLES::178179sage: hyperplane_arrangements.Catalan(5)180Arrangement of 30 hyperplanes of dimension 5 and rank 4181182TESTS::183184sage: h = hyperplane_arrangements.Catalan(5)185sage: h.characteristic_polynomial()186x^5 - 30*x^4 + 335*x^3 - 1650*x^2 + 3024*x187sage: h.characteristic_polynomial.clear_cache() # long time188sage: h.characteristic_polynomial() # long time189x^5 - 30*x^4 + 335*x^3 - 1650*x^2 + 3024*x190"""191H = make_parent(K, n, names)192x = H.gens()193hyperplanes = []194for i in range(n):195for j in range(i+1, n):196for k in [-1, 0, 1]:197hyperplanes.append(x[i] - x[j] - k)198Cn = H(*hyperplanes)199x = polygen(QQ, 'x')200charpoly = x*prod([x-n-i for i in range(1, n)])201Cn.characteristic_polynomial.set_cache(charpoly)202return Cn203204def coordinate(self, n, K=QQ, names=None):205r"""206Return the coordinate hyperplane arrangement.207208INPUT:209210- ``n`` -- integer211212- ``K`` -- field (default: `\QQ`)213214- ``names`` -- tuple of strings or ``None`` (default); the215variable names for the ambient space216217OUTPUT:218219The coordinate hyperplane arrangement, which is the central220hyperplane arrangement consisting of the coordinate221hyperplanes `x_i = 0`.222223EXAMPLES::224225sage: hyperplane_arrangements.coordinate(5)226Arrangement of 5 hyperplanes of dimension 5 and rank 5227"""228H = make_parent(K, n, names)229x = H.gens()230return H(x)231232def G_semiorder(self, G, K=QQ, names=None):233r"""234Return the semiorder hyperplane arrangement of a graph.235236INPUT:237238- ``G`` -- graph239240- ``K`` -- field (default: `\QQ`)241242- ``names`` -- tuple of strings or ``None`` (default); the243variable names for the ambient space244245OUTPUT:246247The semiorder hyperplane arrangement of a graph G is the248arrangement `\{ x_i - x_j = -1,1 \}` where `ij` is an edge of249``G``.250251EXAMPLES::252253sage: G = graphs.CompleteGraph(5)254sage: hyperplane_arrangements.G_semiorder(G)255Arrangement of 20 hyperplanes of dimension 5 and rank 4256sage: g = graphs.HouseGraph()257sage: hyperplane_arrangements.G_semiorder(g)258Arrangement of 12 hyperplanes of dimension 5 and rank 4259"""260n = G.num_verts()261H = make_parent(K, n, names)262x = H.gens()263hyperplanes = []264for e in G.edges():265i = G.vertices().index(e[0])266j = G.vertices().index(e[1])267hyperplanes.append(x[i] - x[j] - 1)268hyperplanes.append(x[i] - x[j] + 1)269return H(*hyperplanes)270271def G_Shi(self, G, K=QQ, names=None):272r"""273Return the Shi hyperplane arrangement of a graph `G`.274275INPUT:276277- ``G`` -- graph278279- ``K`` -- field (default: `\QQ`)280281- ``names`` -- tuple of strings or ``None`` (default); the282variable names for the ambient space283284OUTPUT:285286The Shi hyperplane arrangement of the given graph ``G``.287288EXAMPLES::289290sage: G = graphs.CompleteGraph(5)291sage: hyperplane_arrangements.G_Shi(G)292Arrangement of 20 hyperplanes of dimension 5 and rank 4293sage: g = graphs.HouseGraph()294sage: hyperplane_arrangements.G_Shi(g)295Arrangement of 12 hyperplanes of dimension 5 and rank 4296sage: a = hyperplane_arrangements.G_Shi(graphs.WheelGraph(4)); a297Arrangement of 12 hyperplanes of dimension 4 and rank 3298"""299n = G.num_verts()300H = make_parent(K, n, names)301x = H.gens()302hyperplanes = []303for e in G.edges():304i = G.vertices().index(e[0])305j = G.vertices().index(e[1])306hyperplanes.append(x[i] - x[j])307hyperplanes.append(x[i] - x[j] - 1)308return H(*hyperplanes)309310def graphical(self, G, K=QQ, names=None):311r"""312Return the graphical hyperplane arrangement of a graph ``G``.313314INPUT:315316- ``G`` -- graph317318- ``K`` -- field (default: `\QQ`)319320- ``names`` -- tuple of strings or ``None`` (default); the321variable names for the ambient space322323OUTPUT:324325The graphical hyperplane arrangement of a graph G, which is326the arrangement `\{ x_i - x_j = 0 \}` for all edges `ij` of the327graph ``G``.328329EXAMPLES::330331sage: G = graphs.CompleteGraph(5)332sage: hyperplane_arrangements.graphical(G)333Arrangement of 10 hyperplanes of dimension 5 and rank 4334sage: g = graphs.HouseGraph()335sage: hyperplane_arrangements.graphical(g)336Arrangement of 6 hyperplanes of dimension 5 and rank 4337338TESTS::339340sage: h = hyperplane_arrangements.graphical(g)341sage: h.characteristic_polynomial()342x^5 - 6*x^4 + 14*x^3 - 15*x^2 + 6*x343sage: h.characteristic_polynomial.clear_cache() # long time344sage: h.characteristic_polynomial() # long time345x^5 - 6*x^4 + 14*x^3 - 15*x^2 + 6*x346"""347n = G.num_verts()348H = make_parent(K, n, names)349x = H.gens()350hyperplanes = []351for e in G.edges():352i = G.vertices().index(e[0])353j = G.vertices().index(e[1])354hyperplanes.append(x[i] - x[j])355A = H(*hyperplanes)356charpoly = G.chromatic_polynomial()357A.characteristic_polynomial.set_cache(charpoly)358return A359360def Ish(self, n, K=QQ, names=None):361r"""362Return the Ish arrangement.363364INPUT:365366- ``n`` -- integer367368- ``K`` -- field (default:``QQ``)369370- ``names`` -- tuple of strings or ``None`` (default); the371variable names for the ambient space372373OUTPUT:374375The Ish arrangement, which is the set of `n(n-1)` hyperplanes.376377.. MATH::378379\{ x_i - x_j = 0 : 1 \leq i \leq j \leq n \}380\cup381\{ x_1 - x_j = i : 1 \leq i \leq j \leq n \}.382383EXAMPLES::384385sage: a = hyperplane_arrangements.Ish(3); a386Arrangement of 6 hyperplanes of dimension 3 and rank 2387sage: a.characteristic_polynomial()388x^3 - 6*x^2 + 9*x389sage: b = hyperplane_arrangements.Shi(3)390sage: b.characteristic_polynomial()391x^3 - 6*x^2 + 9*x392393TESTS::394395sage: a.characteristic_polynomial.clear_cache() # long time396sage: a.characteristic_polynomial() # long time397x^3 - 6*x^2 + 9*x398399REFERENCES:400401.. [AR] D. Armstrong, B. Rhoades402"The Shi arrangement and the Ish arrangement"403:arxiv:`1009.1655`404"""405H = make_parent(K, n, names)406x = H.gens()407hyperplanes = []408for i in range(n):409for j in range(i+1, n):410hyperplanes.append(x[i] - x[j])411hyperplanes.append(x[0] - x[j] - (i+1))412A = H(*hyperplanes)413x = polygen(QQ, 'x')414charpoly = x * sum([(-1)**k * stirling_number2(n, n-k) *415prod([(x - 1 - j) for j in range(k, n-1)]) for k in range(0, n)])416A.characteristic_polynomial.set_cache(charpoly)417return A418419def linial(self, n, K=QQ, names=None):420r"""421Return the linial hyperplane arrangement.422423INPUT:424425- ``n`` -- integer426427- ``K`` -- field (default: `\QQ`)428429- ``names`` -- tuple of strings or ``None`` (default); the430variable names for the ambient space431432OUTPUT:433434The linial hyperplane arrangement is the set of hyperplanes435`\{x_i - x_j = 1 : 1\leq i < j \leq n\}`.436437EXAMPLES::438439sage: a = hyperplane_arrangements.linial(4); a440Arrangement of 6 hyperplanes of dimension 4 and rank 3441sage: a.characteristic_polynomial()442x^4 - 6*x^3 + 15*x^2 - 14*x443444TESTS::445446sage: h = hyperplane_arrangements.linial(5)447sage: h.characteristic_polynomial()448x^5 - 10*x^4 + 45*x^3 - 100*x^2 + 90*x449sage: h.characteristic_polynomial.clear_cache() # long time450sage: h.characteristic_polynomial() # long time451x^5 - 10*x^4 + 45*x^3 - 100*x^2 + 90*x452"""453H = make_parent(K, n, names)454x = H.gens()455hyperplanes = []456for i in range(n):457for j in range(i+1, n):458hyperplanes.append(x[i] - x[j] - 1)459A = H(*hyperplanes)460x = polygen(QQ, 'x')461charpoly = x * sum(binomial(n, k)*(x - k)**(n - 1) for k in range(n + 1)) / 2**n462A.characteristic_polynomial.set_cache(charpoly)463return A464465def semiorder(self, n, K=QQ, names=None):466r"""467Return the semiorder arrangement.468469INPUT:470471- ``n`` -- integer472473- ``K`` -- field (default: `\QQ`)474475- ``names`` -- tuple of strings or ``None`` (default); the476variable names for the ambient space477478OUTPUT:479480The semiorder arrangement, which is the set of `n(n-1)`481hyperplanes `\{ x_i - x_j = -1,1 : 1 \leq i \leq j \leq n\}`.482483EXAMPLES::484485sage: hyperplane_arrangements.semiorder(4)486Arrangement of 12 hyperplanes of dimension 4 and rank 3487488TESTS::489490sage: h = hyperplane_arrangements.semiorder(5)491sage: h.characteristic_polynomial()492x^5 - 20*x^4 + 180*x^3 - 790*x^2 + 1380*x493sage: h.characteristic_polynomial.clear_cache() # long time494sage: h.characteristic_polynomial() # long time495x^5 - 20*x^4 + 180*x^3 - 790*x^2 + 1380*x496"""497H = make_parent(K, n, names)498x = H.gens()499hyperplanes = []500for i in range(n):501for j in range(i+1, n):502for k in [-1, 1]:503hyperplanes.append(x[i] - x[j] - k)504A = H(*hyperplanes)505x = polygen(QQ, 'x')506charpoly = x * sum([stirling_number2(n, k) * prod([x - k - i for i in range(1, k)])507for k in range(1, n+1)])508A.characteristic_polynomial.set_cache(charpoly)509return A510511def Shi(self, n, K=QQ, names=None):512r"""513Return the Shi arrangement.514515INPUT:516517- ``n`` -- integer518519- ``K`` -- field (default:``QQ``)520521- ``names`` -- tuple of strings or ``None`` (default); the522variable names for the ambient space523524OUTPUT:525526The Shi arrangement is the set of `n(n-1)` hyperplanes: `\{ x_i - x_j527= 0,1 : 1 \leq i \leq j \leq n \}`.528529EXAMPLES::530531sage: hyperplane_arrangements.Shi(4)532Arrangement of 12 hyperplanes of dimension 4 and rank 3533534TESTS::535536sage: h = hyperplane_arrangements.Shi(4)537sage: h.characteristic_polynomial()538x^4 - 12*x^3 + 48*x^2 - 64*x539sage: h.characteristic_polynomial.clear_cache() # long time540sage: h.characteristic_polynomial() # long time541x^4 - 12*x^3 + 48*x^2 - 64*x542"""543H = make_parent(K, n, names)544x = H.gens()545hyperplanes = []546for i in range(n):547for j in range(i+1, n):548for const in [0, 1]:549hyperplanes.append(x[i] - x[j] - const)550A = H(*hyperplanes)551x = polygen(QQ, 'x')552charpoly = x * sum([(-1)**k * stirling_number2(n, n-k) *553prod([(x - 1 - j) for j in range(k, n-1)]) for k in range(0, n)])554A.characteristic_polynomial.set_cache(charpoly)555return A556557558hyperplane_arrangements = HyperplaneArrangementLibrary()559560561562