Path: blob/master/sage/combinat/crystals/kirillov_reshetikhin.py
4128 views
r"""1Kirillov-Reshetikhin Crystals2"""34#*****************************************************************************5# Copyright (C) 2009 Anne Schilling <anne at math.ucdavis.edu>6#7# Distributed under the terms of the GNU General Public License (GPL)8#9# This code is distributed in the hope that it will be useful,10# but WITHOUT ANY WARRANTY; without even the implied warranty of11# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU12# General Public License for more details.13#14# The full text of the GPL is available at:15#16# http://www.gnu.org/licenses/17#****************************************************************************18# Acknowledgment: most of the design and implementation of this19# library is heavily inspired from MuPAD-Combinat.20#****************************************************************************2122from sage.misc.cachefunc import cached_method23from sage.combinat.combinat import CombinatorialObject24from sage.structure.parent import Parent25from sage.categories.finite_crystals import FiniteCrystals26from sage.rings.integer import Integer27from sage.rings.all import QQ28from sage.functions.other import floor29from sage.misc.functional import is_even, is_odd30from sage.combinat.crystals.affine import AffineCrystalFromClassical, AffineCrystalFromClassicalElement31from sage.combinat.crystals.affine import AffineCrystalFromClassicalAndPromotion32from sage.combinat.crystals.highest_weight_crystals import HighestWeightCrystal33from sage.combinat.crystals.direct_sum import DirectSumOfCrystals34from sage.combinat.root_system.cartan_type import CartanType35from sage.combinat.crystals.tensor_product import CrystalOfTableaux, TensorProductOfCrystals36from sage.combinat.tableau import Tableau37from sage.combinat.partition import Partition, Partitions38from sage.combinat.integer_vector import IntegerVectors39from sage.functions.other import floor, ceil404142def KirillovReshetikhinCrystal(cartan_type, r, s):43r"""44Returns the Kirillov-Reshetikhin crystal `B^{r,s}` of the given type.4546For more information about general crystals see :mod:`sage.combinat.crystals`.4748Many Kirillov-Reshetikhin crystals are constructed from a49classical crystal together with an automorphism `p` on the level of crystals which50corresponds to a Dynkin diagram automorphism mapping node 0 to some other node i.51The action of `f_0` and `e_0` is then constructed using52`f_0 = p^{-1} \circ f_i \circ p`.5354For example, for type `A_n^{(1)}` the Kirillov-Reshetikhin crystal `B^{r,s}`55is obtained from the classical crystal `B(s\omega_r)` using the56promotion operator. For other types, see5758[1] M. Shimozono59"Affine type A crystal structure on tensor products of rectangles,60Demazure characters, and nilpotent varieties",61J. Algebraic Combin. 15 (2002), no. 2, 151-18762(arXiv:math.QA/9804039)6364[2] A. Schilling, "Combinatorial structure of Kirillov-Reshetikhin crystals of65type `D_n(1)`, `B_n(1)`, `A_{2n-1}(2)`", J. Algebra 319 (2008) 2938-296266(arXiv:0704.2046 [math.QA])6768[3] B. Jones, A. Schilling,69""Affine structures and a tableau model for `E_6` crystals",70preprint arXiv:0909.2442 [math.CO]7172Other Kirillov-Reshetikhin crystals are constructed using similarity methods.73See Section 4 of7475[4] G. Fourier, M. Okado, A. Schilling,76"Kirillov-Reshetikhin crystals for nonexceptional types",77Advances in Mathematics 222 Issue 3 (2009) 1080-111678(arXiv:0810.5067 [math.RT])7980INPUT:8182- ``cartan_type`` Affine type and rank8384- ``r`` Label of finite Dynkin diagram8586- ``s`` Positive integer8788EXAMPLES::8990sage: K = KirillovReshetikhinCrystal(['A',3,1], 2, 1)91sage: K.index_set()92[0, 1, 2, 3]93sage: K.list()94[[[1], [2]], [[1], [3]], [[2], [3]], [[1], [4]], [[2], [4]], [[3], [4]]]95sage: b=K(rows=[[1],[2]])96sage: b.weight()97-Lambda[0] + Lambda[2]9899sage: K = KirillovReshetikhinCrystal(['A',3,1], 2,2)100sage: K.automorphism(K.module_generators[0])101[[2, 2], [3, 3]]102sage: K.module_generators[0].e(0)103[[1, 2], [2, 4]]104sage: K.module_generators[0].f(2)105[[1, 1], [2, 3]]106sage: K.module_generators[0].f(1)107sage: K.module_generators[0].phi(0)1080109sage: K.module_generators[0].phi(1)1100111sage: K.module_generators[0].phi(2)1122113sage: K.module_generators[0].epsilon(0)1142115sage: K.module_generators[0].epsilon(1)1160117sage: K.module_generators[0].epsilon(2)1180119sage: b = K(rows=[[1,2],[2,3]])120sage: b121[[1, 2], [2, 3]]122sage: b.f(2)123[[1, 2], [3, 3]]124125sage: K = KirillovReshetikhinCrystal(['D',4,1], 2, 1)126sage: K.cartan_type()127['D', 4, 1]128sage: type(K.module_generators[0])129<class 'sage.combinat.crystals.affine.KR_type_vertical_with_category.element_class'>130131132The following gives some tests with regards to Lemma 3.11 in133134[5] C. Lecouvey, M. Okado, M. Shimozono,135"Affine crystals, one-dimensional sums and parabolic Lusztig `q`-analogues'136preprint arXiv:1002.3715137138TESTS::139140sage: K = KirillovReshetikhinCrystal(['A',4,2],2,1)141sage: Lambda = K.weight_lattice_realization().fundamental_weights()142sage: [b for b in K if b.Epsilon() == Lambda[0]]143[[]]144145sage: K = KirillovReshetikhinCrystal(['D',4,2],1,2)146sage: Lambda = K.weight_lattice_realization().fundamental_weights()147sage: [b for b in K if b.Epsilon() == 2*Lambda[0]]148[[]]149sage: [b for b in K if b.Epsilon() == 2*Lambda[3]]150[[[3, -3]]]151sage: K = KirillovReshetikhinCrystal(['D',4,2],1,1)152sage: [b for b in K if b.Epsilon() == Lambda[3]]153[[[0]]]154155sage: K = KirillovReshetikhinCrystal(['B',3,1],2,1)156sage: Lambda = K.weight_lattice_realization().fundamental_weights()157sage: [b for b in K if b.Epsilon() == Lambda[0]]158[[]]159sage: [b for b in K if b.Epsilon() == Lambda[1]]160[[[2], [-2]]]161sage: K = KirillovReshetikhinCrystal(['B',3,1],2,2)162sage: [b for b in K if b.Epsilon() == 2*Lambda[0]]163[[]]164sage: [b for b in K if b.Epsilon() == 2*Lambda[1]]165[[[1, 2], [-2, -1]]]166sage: K = KirillovReshetikhinCrystal(['B',3,1],2,3)167sage: [b for b in K if b.Epsilon() == 3*Lambda[1]] # long time168[[[1, 2, 2], [-2, -2, -1]]]169170sage: K = KirillovReshetikhinCrystal(['D',4,1],2,2)171sage: Lambda = K.weight_lattice_realization().fundamental_weights()172sage: [b for b in K if b.Epsilon() == 2*Lambda[0]] # long time173[[]]174sage: [b for b in K if b.Epsilon() == 2*Lambda[4]] # long time175[[[3, -4], [4, -3]]]176177sage: K = KirillovReshetikhinCrystal(['B',3,1],3,1)178sage: Lambda = K.weight_lattice_realization().fundamental_weights()179sage: [b for b in K if b.Epsilon() == Lambda[0]]180[[+++, []]]181sage: [b for b in K if b.Epsilon() == Lambda[1]]182[[-++, []]]183sage: K = KirillovReshetikhinCrystal(['B',3,1],3,3)184sage: [b for b in K if b.Epsilon() == 2*Lambda[0]] # long time185[[+++, [[1]]]]186sage: [b for b in K if b.Epsilon() == 2*Lambda[1]] # long time187[[-++, [[-1]]]]188189sage: K = KirillovReshetikhinCrystal(['B',4,1],4,1)190sage: Lambda = K.weight_lattice_realization().fundamental_weights()191sage: [b for b in K if b.Epsilon() == Lambda[0]]192[[++++, []]]193sage: [b for b in K if b.Epsilon() == Lambda[1]]194[[-+++, []]]195196sage: K = KirillovReshetikhinCrystal(['C',3,1],1,1)197sage: Lambda = K.weight_lattice_realization().fundamental_weights()198sage: [b for b in K if b.Epsilon() == Lambda[0]]199[[[1]]]200sage: [b for b in K if b.Epsilon() == Lambda[3]]201[[[-3]]]202sage: K = KirillovReshetikhinCrystal(['C',3,1],1,3)203sage: [b for b in K if b.Epsilon() == 2*Lambda[3]] # long time204[[[3, -3, -3]]]205sage: [b for b in K if b.Epsilon() == 2*Lambda[0]] # long time206[[[1]]]207"""208ct = CartanType(cartan_type)209assert ct.is_affine()210if ct.is_untwisted_affine():211if ct.type() == 'A':212return KR_type_A(ct, r, s)213elif ct.type() == 'D' and r<ct.rank()-2:214return KR_type_vertical(ct, r, s)215elif ct.type() == 'B':216if r<ct.rank()-1:217return KR_type_vertical(ct, r, s)218elif r == ct.rank()-1:219return KR_type_Bn(ct, r, s)220else:221raise ValueError("wrong range of parameters")222elif ct.type() == 'C':223if r<ct.rank()-1:224return KR_type_C(ct, r, s)225elif r == ct.rank()-1:226return KR_type_Cn(ct, r, s)227else:228raise ValueError("wrong range of parameters")229elif ct == CartanType(['E',6,1]) and r in [1,6,2]:230return KR_type_E6(ct, r, s)231else:232raise NotImplementedError233else:234if ct.dual().type() == 'B':235return KR_type_vertical(ct, r, s)236elif ct.type() == 'BC':237return KR_type_box(ct, r, s)238elif ct.dual().type() == 'BC':239return KR_type_A2(ct, r, s)240elif ct.dual().type() == 'C':241if r<ct.rank()-1:242return KR_type_box(ct, r, s)243elif r == ct.rank()-1:244return KR_type_Dn_twisted(ct, r, s)245else:246raise ValueError("wrong range of parameters")247else:248raise NotImplementedError249250251class KirillovReshetikhinGenericCrystal(Parent):252r"""253Generic class for Kirillov-Reshetikhin crystal `B^{r,s}` of the given type.254255Input is a Dynkin node `r`, a positive integer `s`, and a Cartan type `cartan_type`.256"""257258def __init__(self, cartan_type, r, s, dual = None):259r"""260Initializes a generic Kirillov-Reshetikhin crystal.261262TESTS::263264sage: K = sage.combinat.crystals.kirillov_reshetikhin.KirillovReshetikhinGenericCrystal(CartanType(['A',2,1]), 1, 1)265sage: K266Kirillov-Reshetikhin crystal of type ['A', 2, 1] with (r,s)=(1,1)267sage: K.r()2681269sage: K.s()2701271"""272Parent.__init__(self, category = FiniteCrystals())273if dual is None:274self._cartan_type = cartan_type275else:276self._cartan_type = CartanType(cartan_type).dual()277self._r = r278self._s = s279self._dual = dual280281def _repr_(self):282"""283EXAMPLES::284285sage: sage.combinat.crystals.kirillov_reshetikhin.KirillovReshetikhinGenericCrystal(CartanType(['A',2,1]), 1, 1) # indirect doctest286Kirillov-Reshetikhin crystal of type ['A', 2, 1] with (r,s)=(1,1)287"""288return "Kirillov-Reshetikhin crystal of type %s with (r,s)=(%d,%d)" % (self.cartan_type(), self.r(), self.s())289290def module_generator(self):291r"""292Yields the module generator of weight `s \Lambda_r` of a Kirillov-Reshetikhin crystal `B^{r,s}`293294EXAMPLES::295296sage: K = KirillovReshetikhinCrystal(['C',2,1],1,2)297sage: K.module_generator()298[[1, 1]]299sage: K = KirillovReshetikhinCrystal(['E',6,1],1,1)300sage: K.module_generator()301[[1]]302303sage: K = KirillovReshetikhinCrystal(['D',4,1],2,1)304sage: K.module_generator()305[[1], [2]]306"""307R = self.weight_lattice_realization()308Lambda = R.fundamental_weights()309r = self.r()310s = self.s()311c = R.null_coroot()[r]312return [ b for b in self.module_generators if b.weight() == s*Lambda[r] - s*c*Lambda[0] ][0]313314def r(self):315"""316Returns r of the underlying Kirillov-Reshetikhin crystal `B^{r,s}`317318EXAMPLES::319320sage: K = KirillovReshetikhinCrystal(['D',4,1], 2, 1)321sage: K.r()3222323"""324return self._r325326def s(self):327"""328Returns s of the underlying Kirillov-Reshetikhin crystal `B^{r,s}`329330EXAMPLES::331332sage: K = KirillovReshetikhinCrystal(['D',4,1], 2, 1)333sage: K.s()3341335"""336return self._s337338def is_perfect(self):339r"""340Returns True or False depending on whether ``self`` is a perfect crystal or not, respectively.341342If ``self`` is the Kirillov-Reshetikhin crystal `B^{r,s}`, then it was proven in [FOS2010]_343that it is perfect if and only if `s/c_r` is an integer (where `c_r` is a constant related to the344type of the crystal).345346REFERENCES:347348.. [FOS2010] G. Fourier, M. Okado, A. Schilling.349Perfectness of Kirillov-Reshetikhin crystals for nonexceptional types350Contemp. Math. 506 (2010) 127-143 ( arXiv:0811.1604 [math.RT] )351352EXAMPLES::353354sage: K = KirillovReshetikhinCrystal(['A',2,1], 1, 1)355sage: K.is_perfect()356True357358sage: K = KirillovReshetikhinCrystal(['C',2,1], 1, 1)359sage: K.is_perfect()360False361362sage: K = KirillovReshetikhinCrystal(['C',2,1], 1, 2)363sage: K.is_perfect()364True365"""366x = self.s()/self.cartan_type().c()[self.r()]367return x - ceil(x) == 0368369def level(self):370r"""371Returns the level of ``self`` assuming that it is a perfect crystal.372373If ``self`` is the Kirillov-Reshetikhin crystal `B^{r,s}`, then it was proven in [FOS2010]_374that its level is `s/c_r` which is an integer if ``self`` is perfect375(here `c_r` is a constant related to the type of the crystal).376377EXAMPLES::378379sage: K = KirillovReshetikhinCrystal(['A',2,1], 1, 1)380sage: K.level()3811382sage: K = KirillovReshetikhinCrystal(['C',2,1], 1, 2)383sage: K.level()3841385sage: K = KirillovReshetikhinCrystal(['D',4,1], 1, 3)386sage: K.level()3873388389sage: K = KirillovReshetikhinCrystal(['C',2,1], 1, 1)390sage: K.level()391Traceback (most recent call last):392...393AssertionError: This crystal is not perfect!394"""395assert self.is_perfect(), "This crystal is not perfect!"396return self.s()/self.cartan_type().c()[self.r()]397398def R_matrix(self, K):399r"""400INPUT:401402- ``self`` -- a crystal `L`403- ``K`` -- a Kirillov-Reshetikhin crystal of the same type as `L`.404405Returns the *combinatorial `R`-matrix* from `L \otimes K \to K406\otimes L`, where the combinatorial `R`-matrix is the affine407crystal isomorphism which maps `u_{L} \otimes u_K` to `u_K408\otimes u_{L}`, where `u_K` is the unique element in `K =409B^{r,s}` of weight `s\Lambda_r - s c \Lambda_0` (see410module_generator).411412EXAMPLES::413414sage: K = KirillovReshetikhinCrystal(['A',2,1],1,1)415sage: L = KirillovReshetikhinCrystal(['A',2,1],1,2)416sage: f = K.R_matrix(L)417sage: [[b,f(b)] for b in TensorProductOfCrystals(K,L)]418[[[[[1]], [[1, 1]]], [[[1, 1]], [[1]]]],419[[[[1]], [[1, 2]]], [[[1, 1]], [[2]]]],420[[[[1]], [[2, 2]]], [[[1, 2]], [[2]]]],421[[[[1]], [[1, 3]]], [[[1, 1]], [[3]]]],422[[[[1]], [[2, 3]]], [[[1, 2]], [[3]]]],423[[[[1]], [[3, 3]]], [[[1, 3]], [[3]]]],424[[[[2]], [[1, 1]]], [[[1, 2]], [[1]]]],425[[[[2]], [[1, 2]]], [[[2, 2]], [[1]]]],426[[[[2]], [[2, 2]]], [[[2, 2]], [[2]]]],427[[[[2]], [[1, 3]]], [[[2, 3]], [[1]]]],428[[[[2]], [[2, 3]]], [[[2, 2]], [[3]]]],429[[[[2]], [[3, 3]]], [[[2, 3]], [[3]]]],430[[[[3]], [[1, 1]]], [[[1, 3]], [[1]]]],431[[[[3]], [[1, 2]]], [[[1, 3]], [[2]]]],432[[[[3]], [[2, 2]]], [[[2, 3]], [[2]]]],433[[[[3]], [[1, 3]]], [[[3, 3]], [[1]]]],434[[[[3]], [[2, 3]]], [[[3, 3]], [[2]]]],435[[[[3]], [[3, 3]]], [[[3, 3]], [[3]]]]]436437sage: K = KirillovReshetikhinCrystal(['D',4,1],1,1)438sage: L = KirillovReshetikhinCrystal(['D',4,1],2,1)439sage: f = K.R_matrix(L)440sage: T = TensorProductOfCrystals(K,L)441sage: b = T( K(rows=[[1]]), L(rows=[]) )442sage: f(b)443[[[2], [-2]], [[1]]]444445Alternatively, one can compute the combinatorial `R`-matrix using the isomorphism method446of digraphs::447448sage: K1 = KirillovReshetikhinCrystal(['A',2,1],1,1)449sage: K2 = KirillovReshetikhinCrystal(['A',2,1],2,1)450sage: T1 = TensorProductOfCrystals(K1,K2)451sage: T2 = TensorProductOfCrystals(K2,K1)452sage: T1.digraph().is_isomorphic(T2.digraph(), edge_labels = True, certify = True) #todo: not implemented (see #10904 and #10549)453(True, {[[[1]], [[2], [3]]]: [[[1], [3]], [[2]]], [[[3]], [[2], [3]]]: [[[2], [3]], [[3]]],454[[[3]], [[1], [3]]]: [[[1], [3]], [[3]]], [[[1]], [[1], [3]]]: [[[1], [3]], [[1]]], [[[1]],455[[1], [2]]]: [[[1], [2]], [[1]]], [[[2]], [[1], [2]]]: [[[1], [2]], [[2]]], [[[3]],456[[1], [2]]]: [[[2], [3]], [[1]]], [[[2]], [[1], [3]]]: [[[1], [2]], [[3]]], [[[2]], [[2], [3]]]: [[[2], [3]], [[2]]]})457"""458T1 = TensorProductOfCrystals(self, K)459T2 = TensorProductOfCrystals(K, self)460gen1 = T1( self.module_generator(), K.module_generator() )461gen2 = T2( K.module_generator(), self.module_generator() )462g = { gen1 : gen2 }463return T1.crystal_morphism(g, acyclic = False)464465466class KirillovReshetikhinCrystalFromPromotion(KirillovReshetikhinGenericCrystal, AffineCrystalFromClassicalAndPromotion):467r"""468This generic class assumes that the Kirillov-Reshetikhin crystal is constructed469from a classical crystal 'classical_decomposition' and an automorphism 'promotion' and its inverse470which corresponds to a Dynkin diagram automorphism 'dynkin_diagram_automorphism'.471472Each instance using this class needs to implement the methods:473- classical_decomposition474- promotion475- promotion_inverse476- dynkin_diagram_automorphism477"""478def __init__(self, cartan_type, r, s):479r"""480TESTS::481482sage: K = KirillovReshetikhinCrystal(['B',2,1], 1, 1)483sage: K484Kirillov-Reshetikhin crystal of type ['B', 2, 1] with (r,s)=(1,1)485sage: TestSuite(K).run()486"""487KirillovReshetikhinGenericCrystal.__init__(self, cartan_type, r ,s)488AffineCrystalFromClassicalAndPromotion.__init__(self, cartan_type, self.classical_decomposition(),489self.promotion(), self.promotion_inverse(),490self.dynkin_diagram_automorphism(0))491492493class KR_type_A(KirillovReshetikhinCrystalFromPromotion):494r"""495Class of Kirillov-Reshetikhin crystals of type `A_n^{(1)}`.496497EXAMPLES::498499sage: K = KirillovReshetikhinCrystal(['A',3,1], 2,2)500sage: b = K(rows=[[1,2],[2,4]])501sage: b.f(0)502[[1, 1], [2, 2]]503"""504505def classical_decomposition(self):506"""507Specifies the classical crystal underlying the KR crystal of type A.508509EXAMPLES::510511sage: K = KirillovReshetikhinCrystal(['A',3,1], 2,2)512sage: K.classical_decomposition()513The crystal of tableaux of type ['A', 3] and shape(s) [[2, 2]]514"""515return CrystalOfTableaux(self.cartan_type().classical(), shape = [self.s() for i in range(1,self.r()+1)])516517def promotion(self):518"""519Specifies the promotion operator used to construct the affine type A crystal.520For type A this corresponds to the Dynkin diagram automorphism which maps i to i+1 mod n+1,521where n is the rank.522523EXAMPLES::524525sage: K = KirillovReshetikhinCrystal(['A',3,1], 2,2)526sage: b = K.classical_decomposition()(rows=[[1,2],[3,4]])527sage: K.promotion()(b)528[[1, 3], [2, 4]]529"""530return lambda x : self.classical_crystal(x.to_tableau().promotion(self._cartan_type[1]))531532def promotion_inverse(self):533"""534Specifies the inverse promotion operator used to construct the affine type A crystal.535For type A this corresponds to the Dynkin diagram automorphism which maps i to i-1 mod n+1,536where n is the rank.537538EXAMPLES::539540sage: K = KirillovReshetikhinCrystal(['A',3,1], 2,2)541sage: b = K.classical_decomposition()(rows=[[1,3],[2,4]])542sage: K.promotion_inverse()(b)543[[1, 2], [3, 4]]544sage: b = K.classical_decomposition()(rows=[[1,2],[3,3]])545sage: K.promotion_inverse()(K.promotion()(b))546[[1, 2], [3, 3]]547"""548return lambda x : self.classical_crystal(x.to_tableau().promotion_inverse(self._cartan_type[1]))549550def dynkin_diagram_automorphism(self, i):551"""552Specifies the Dynkin diagram automorphism underlying the promotion action on the crystal553elements. The automorphism needs to map node 0 to some other Dynkin node.554555For type A we use the Dynkin diagram automorphism which maps i to i+1 mod n+1, where n is the rank.556557EXAMPLES::558559sage: K = KirillovReshetikhinCrystal(['A',3,1], 2,2)560sage: K.dynkin_diagram_automorphism(0)5611562sage: K.dynkin_diagram_automorphism(3)5630564"""565aut = range(1,self.cartan_type().rank())+[0]566return aut[i]567568class KR_type_vertical(KirillovReshetikhinCrystalFromPromotion):569r"""570Class of Kirillov-Reshetikhin crystals `B^{r,s}` of type `D_n^{(1)}` for `r\le n-2`,571`B_n^{(1)}` for `r<n`, and `A_{2n-1}^{(2)}` for `r\le n`.572573EXAMPLES::574575sage: K = KirillovReshetikhinCrystal(['D',4,1], 2,2)576sage: b = K(rows=[])577sage: b.f(0)578[[1], [2]]579sage: b.f(0).f(0)580[[1, 1], [2, 2]]581sage: b.e(0)582[[-2], [-1]]583sage: b.e(0).e(0)584[[-2, -2], [-1, -1]]585586sage: K = KirillovReshetikhinCrystal(['D',5,1], 3,1)587sage: b = K(rows=[[1]])588sage: b.e(0)589[[3], [-3], [-2]]590591sage: K = KirillovReshetikhinCrystal(['B',3,1], 1,1)592sage: [[b,b.f(0)] for b in K]593[[[[1]], None], [[[2]], None], [[[3]], None], [[[0]], None], [[[-3]], None], [[[-2]], [[1]]], [[[-1]], [[2]]]]594595sage: K = KirillovReshetikhinCrystal(['A',5,2], 1,1)596sage: [[b,b.f(0)] for b in K]597[[[[1]], None], [[[2]], None], [[[3]], None], [[[-3]], None], [[[-2]], [[1]]], [[[-1]], [[2]]]]598"""599600def classical_decomposition(self):601r"""602Specifies the classical crystal underlying the Kirillov-Reshetikhin crystal of type `D_n^{(1)}`,603`B_n^{(1)}`, and `A_{2n-1}^{(2)}`.604It is given by `B^{r,s} \cong \oplus_\Lambda B(\Lambda)` where `\Lambda` are weights obtained from605a rectangle of width s and height r by removing verticle dominoes. Here we identify the fundamental606weight `\Lambda_i` with a column of height `i`.607608EXAMPLES::609610sage: K = KirillovReshetikhinCrystal(['D',4,1], 2,2)611sage: K.classical_decomposition()612The crystal of tableaux of type ['D', 4] and shape(s) [[], [1, 1], [2, 2]]613"""614return CrystalOfTableaux(self.cartan_type().classical(),615shapes = vertical_dominoes_removed(self.r(),self.s()))616617def promotion(self):618"""619Specifies the promotion operator used to construct the affine type `D_n^{(1)}` etc. crystal.620This corresponds to the Dynkin diagram automorphism which interchanges nodes 0 and 1,621and leaves all other nodes unchanged. On the level of crystals it is constructed using622`\pm` diagrams.623624EXAMPLES::625626sage: K = KirillovReshetikhinCrystal(['D',4,1], 2,2)627sage: promotion = K.promotion()628sage: b = K.classical_decomposition()(rows=[])629sage: promotion(b)630[[1, 2], [-2, -1]]631sage: b = K.classical_decomposition()(rows=[[1,3],[2,-1]])632sage: promotion(b)633[[1, 3], [2, -1]]634sage: b = K.classical_decomposition()(rows=[[1],[-3]])635sage: promotion(b)636[[2, -3], [-2, -1]]637"""638T = self.classical_decomposition()639ind = T.index_set()640ind.remove(1)641return T.crystal_morphism( self.promotion_on_highest_weight_vectors(), index_set = ind)642643promotion_inverse = promotion644645def dynkin_diagram_automorphism(self, i):646"""647Specifies the Dynkin diagram automorphism underlying the promotion action on the crystal648elements. The automorphism needs to map node 0 to some other Dynkin node.649650Here we use the Dynkin diagram automorphism which interchanges nodes 0 and 1 and leaves651all other nodes unchanged.652653EXAMPLES::654655sage: K = KirillovReshetikhinCrystal(['D',4,1],1,1)656sage: K.dynkin_diagram_automorphism(0)6571658sage: K.dynkin_diagram_automorphism(1)6590660sage: K.dynkin_diagram_automorphism(4)6614662"""663aut = [1,0]+range(2,self.cartan_type().rank())664return aut[i]665666def promotion_on_highest_weight_vectors(self):667"""668Calculates promotion on `{2,3,...,n}` highest weight vectors.669670EXAMPLES::671672sage: K = KirillovReshetikhinCrystal(['D',4,1], 2,2)673sage: T = K.classical_decomposition()674sage: hw = [ b for b in T if all(b.epsilon(i)==0 for i in [2,3,4]) ]675sage: [K.promotion_on_highest_weight_vectors()(b) for b in hw]676[[[1, 2], [-2, -1]], [[2, 2], [-2, -1]], [[1, 2], [3, -1]], [[2], [-2]],677[[1, 2], [2, -2]], [[2, 2], [-1, -1]], [[2, 2], [3, -1]], [[2, 2], [3, 3]],678[], [[1], [2]], [[1, 1], [2, 2]], [[2], [-1]], [[1, 2], [2, -1]], [[2], [3]],679[[1, 2], [2, 3]]]680"""681return lambda b: self.from_pm_diagram_to_highest_weight_vector(self.from_highest_weight_vector_to_pm_diagram(b).sigma())682683def from_highest_weight_vector_to_pm_diagram(self, b):684"""685This gives the bijection between an element b in the classical decomposition686of the KR crystal that is `{2,3,..,n}`-highest weight and `\pm` diagrams.687688EXAMPLES::689690sage: K = KirillovReshetikhinCrystal(['D',4,1], 2,2)691sage: T = K.classical_decomposition()692sage: b = T(rows=[[2],[-2]])693sage: pm = K.from_highest_weight_vector_to_pm_diagram(b); pm694[[1, 1], [0, 0], [0]]695sage: pm.__repr__(pretty_printing=True)696+697-698sage: b = T(rows=[])699sage: pm=K.from_highest_weight_vector_to_pm_diagram(b); pm700[[0, 2], [0, 0], [0]]701sage: pm.__repr__(pretty_printing=True)702703sage: hw = [ b for b in T if all(b.epsilon(i)==0 for i in [2,3,4]) ]704sage: all(K.from_pm_diagram_to_highest_weight_vector(K.from_highest_weight_vector_to_pm_diagram(b)) == b for b in hw)705True706"""707n = self.cartan_type().rank()-1708inner = Partition([Integer(b.weight()[i]) for i in range(1,n+1)])709inter = Partition([len([i for i in r if i>0]) for r in b.to_tableau()])710outer = b.to_tableau().shape()711return PMDiagram([self.r(), self.s(), outer, inter, inner], from_shapes=True)712713def from_pm_diagram_to_highest_weight_vector(self, pm):714"""715This gives the bijection between a `\pm` diagram and an element b in the classical716decomposition of the KR crystal that is {2,3,..,n}-highest weight.717718EXAMPLES::719720sage: K = KirillovReshetikhinCrystal(['D',4,1], 2,2)721sage: pm = sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[1, 1], [0, 0], [0]])722sage: K.from_pm_diagram_to_highest_weight_vector(pm)723[[2], [-2]]724"""725u = [b for b in self.classical_decomposition().module_generators if b.to_tableau().shape() == pm.outer_shape()][0]726ct = self.cartan_type()727rank = ct.rank()-1728ct_type = ct.classical().type()729assert ct_type in ['B', 'C', 'D']730list = []731for h in pm.heights_of_addable_plus():732list += range(1,h+1)733for h in pm.heights_of_minus():734if ct_type == 'D':735list += range(1,rank+1)+[rank-2-k for k in range(rank-1-h)]736elif ct_type == 'B':737list += range(1,rank+1)+[rank-k for k in range(rank+1-h)]738else:739list += range(1,rank+1)+[rank-1-k for k in range(rank-h)]740for i in reversed(list):741u = u.f(i)742return u743744class KR_type_E6(KirillovReshetikhinCrystalFromPromotion):745r"""746Class of Kirillov-Reshetikhin crystals of type `E_6^{(1)}` for `r=1,2,6`.747748EXAMPLES::749750sage: K = KirillovReshetikhinCrystal(['E',6,1],2,1)751sage: K.module_generator().e(0)752[]753sage: K.module_generator().e(0).f(0)754[[[2, -1], [1]]]755sage: K = KirillovReshetikhinCrystal(['E',6,1], 1,1)756sage: b = K.module_generator()757sage: b758[[1]]759sage: b.e(0)760[[-2, 1]]761sage: b = [t for t in K if t.epsilon(1) == 1 and t.phi(3) == 1 and t.phi(2) == 0 and t.epsilon(2) == 0][0]762sage: b763[[-1, 3]]764sage: b.e(0)765[[-1, -2, 3]]766767The elements of the Kirillov-Reshetikhin crystals can be constructed from a classical768crystal element using :meth:`rectract`.769770EXAMPLES::771772sage: K = KirillovReshetikhinCrystal(['E',6,1],2,1)773sage: La = K.cartan_type().classical().root_system().weight_lattice().fundamental_weights()774sage: H = HighestWeightCrystal(La[2])775sage: t = H.module_generator()776sage: t777[[[2, -1], [1]]]778sage: type(K.retract(t))779<class 'sage.combinat.crystals.affine.KR_type_E6_with_category.element_class'>780sage: K.retract(t).e(0)781[]782783TESTS::784785sage: K = KirillovReshetikhinCrystal(['E',6,1], 2,1)786sage: La = K.weight_lattice_realization().fundamental_weights()787sage: all(b.weight() == sum( (K.affine_weight(b.lift())[i] * La[i] for i in K.index_set()), 0*La[0]) for b in K) # long time (26s on sage.math, 2011)788True789"""790791def classical_decomposition(self):792"""793Specifies the classical crystal underlying the KR crystal of type `E_6^{(1)}`.794795EXAMPLES::796797sage: K = KirillovReshetikhinCrystal(['E',6,1], 2,2)798sage: K.classical_decomposition()799Direct sum of the crystals Family (Finite dimensional highest weight crystal of type ['E', 6] and highest weight 0, Finite dimensional highest weight crystal of type ['E', 6] and highest weight Lambda[2], Finite dimensional highest weight crystal of type ['E', 6] and highest weight 2*Lambda[2])800sage: K = KirillovReshetikhinCrystal(['E',6,1], 1,2)801sage: K.classical_decomposition()802Direct sum of the crystals Family (Finite dimensional highest weight crystal of type ['E', 6] and highest weight 2*Lambda[1],)803"""804La = self.cartan_type().classical().root_system().weight_lattice().fundamental_weights()805if self.r() in [1,6]:806dw = [self.s()*La[self.r()]]807elif self.r() == 2:808dw = sum( ([k*La[2]] for k in range(self.s()+1)), [])809else:810raise ValueError811return DirectSumOfCrystals([HighestWeightCrystal(dominant_weight) for dominant_weight in dw], keepkey = False)812813def dynkin_diagram_automorphism(self, i):814r"""815Specifies the Dynkin diagram automorphism underlying the promotion action on the crystal816elements. The automorphism needs to map node 0 to some other Dynkin node.817818Here we use the Dynkin diagram automorphism of order 3 which maps node 0 to node 1.819820EXAMPLES::821822sage: K = KirillovReshetikhinCrystal(['E',6,1],2,1)823sage: [K.dynkin_diagram_automorphism(i) for i in K.index_set()]824[1, 6, 3, 5, 4, 2, 0]825"""826aut = [1,6,3,5,4,2,0]827return aut[i]828829def affine_weight(self, b):830r"""831Returns the affine level zero weight corresponding to the element b of the classical832crystal underlying self. For the coefficients to calculate the level, see Kac pg. 48.833834EXAMPLES::835836sage: K = KirillovReshetikhinCrystal(['E',6,1],2,1)837sage: [K.affine_weight(x.lift()) for x in K if all(x.epsilon(i) == 0 for i in [2,3,4,5])]838[(0, 0, 0, 0, 0, 0, 0),839(-2, 0, 1, 0, 0, 0, 0),840(-1, -1, 0, 0, 0, 1, 0),841(0, 0, 0, 0, 0, 0, 0),842(0, 0, 0, 0, 0, 1, -2),843(0, -1, 1, 0, 0, 0, -1),844(-1, 0, 0, 1, 0, 0, -1),845(-1, -1, 0, 0, 1, 0, -1),846(0, 0, 0, 0, 0, 0, 0),847(0, -2, 0, 1, 0, 0, 0)]848"""849simple_roots = self.cartan_type().classical().root_system().ambient_space().simple_roots()850index_set = b.parent().index_set()851weight = [ Integer(b.weight().scalar( simple_roots[i] )) for i in index_set ]852E6_coeffs = [ 1, 2, 2, 3, 2, 1 ]853return tuple( [-sum([ weight[i-1] * E6_coeffs[i-1] for i in index_set ])] + weight )854855856@cached_method857def hw_auxiliary(self):858r"""859Returns the `{2,3,4,5}` highest weight elements of self.860861EXAMPLES::862863sage: K = KirillovReshetikhinCrystal(['E',6,1],2,1)864sage: K.hw_auxiliary()865[[], [[[2, -1], [1]]], [[[5, -3], [-1, 3]]], [[[6, -2], [-6, 2]]],866[[[5, -2, -6], [-6, 2]]], [[[-1], [-6, 2]]], [[[3, -1, -6], [1]]],867[[[4, -3, -6], [-1, 3]]], [[[1, -3], [-1, 3]]], [[[-1], [-1, 3]]]]868"""869return [x for x in self.classical_decomposition() if all(x.epsilon(i) == 0 for i in [2,3,4,5])]870871@cached_method872def highest_weight_dict(self):873r"""874Returns a dictionary between `{1,2,3,4,5}` highest weight elements, and a tuple of affine weights and its classical component.875876EXAMPLES::877878sage: K = KirillovReshetikhinCrystal(['E',6,1],2,1)879sage: K.highest_weight_dict()880{[[[3, -1, -6], [1]]]: ((-1, 0, 0, 1, 0, 0, -1), 1),881[[[5, -2, -6], [-6, 2]]]: ((0, 0, 0, 0, 0, 1, -2), 1),882[[[2, -1], [1]]]: ((-2, 0, 1, 0, 0, 0, 0), 1),883[[[6, -2], [-6, 2]]]: ((0, 0, 0, 0, 0, 0, 0), 1),884[]: ((0, 0, 0, 0, 0, 0, 0), 0)}885"""886hw = [x for x in self.hw_auxiliary() if x.epsilon(1) == 0]887dic = dict( ( x, tuple( [self.affine_weight(x), len(x)] ) ) for x in hw )888assert len(hw) == len(dic)889return dic890891@cached_method892def highest_weight_dict_inv(self):893r"""894Returns a dictionary between a tuple of affine weights and a classical component, and895`{2,3,4,5,6}` highest weight elements.896897EXAMPLES::898899sage: K = KirillovReshetikhinCrystal(['E',6,1],2,1)900sage: K.highest_weight_dict_inv()901{((0, 0, 0, 0, 0, 0, 0), 0): [],902((-1, -1, 0, 0, 0, 1, 0), 1): [[[5, -3], [-1, 3]]],903((0, 0, 0, 0, 0, 0, 0), 1): [[[1, -3], [-1, 3]]],904((0, -2, 0, 1, 0, 0, 0), 1): [[[-1], [-1, 3]]],905((-2, 0, 1, 0, 0, 0, 0), 1): [[[2, -1], [1]]]}906"""907hw = [x for x in self.hw_auxiliary() if x.epsilon(6) == 0]908dic = dict( ( tuple( [self.affine_weight(x), len(x)] ), x ) for x in hw )909assert len(hw) == len(dic)910return dic911912def automorphism_on_affine_weight(self, weight):913r"""914Acts with the Dynkin diagram automorphism on affine weights as outputted by the affine_weight method.915916EXAMPLES::917918sage: K = KirillovReshetikhinCrystal(['E',6,1],2,1)919sage: [[x[0], K.automorphism_on_affine_weight(x[0])] for x in K.highest_weight_dict().values()]920[[(-1, 0, 0, 1, 0, 0, -1), (-1, -1, 0, 0, 0, 1, 0)],921[(0, 0, 0, 0, 0, 1, -2), (-2, 0, 1, 0, 0, 0, 0)],922[(-2, 0, 1, 0, 0, 0, 0), (0, -2, 0, 1, 0, 0, 0)],923[(0, 0, 0, 0, 0, 0, 0), (0, 0, 0, 0, 0, 0, 0)],924[(0, 0, 0, 0, 0, 0, 0), (0, 0, 0, 0, 0, 0, 0)]]925"""926f = self.dynkin_diagram_automorphism927return tuple( [weight[f(f(i))] for i in self.index_set()] )928929def promotion_on_highest_weight_vectors(self):930r"""931Gives a dictionary of the promotion map on `{1,2,3,4,5}` highest weight elements to932`{2,3,4,5,6}` elements in self.933934EXAMPLES::935936sage: K = KirillovReshetikhinCrystal(['E',6,1],2,1)937sage: dic = K.promotion_on_highest_weight_vectors()938sage: dic939{[[[2, -1], [1]]]: [[[-1], [-1, 3]]],940[[[5, -2, -6], [-6, 2]]]: [[[2, -1], [1]]],941[[[3, -1, -6], [1]]]: [[[5, -3], [-1, 3]]],942[[[6, -2], [-6, 2]]]: [], []: [[[1, -3], [-1, 3]]]}943"""944dic = self.highest_weight_dict()945dic_inv = self.highest_weight_dict_inv()946dic_weight = {}947for (weight, i) in dic.values():948dic_weight[weight] = dic_weight.get(weight, []) + [i]949map_index = lambda (i, list) : max(list)+min(list)-i950map_element = lambda x : tuple([self.automorphism_on_affine_weight(dic[x][0]), map_index((dic[x][1],dic_weight[dic[x][0]]))])951return dict( (x, dic_inv[map_element(x)]) for x in dic.keys() )952953def promotion_on_highest_weight_vectors_function(self):954return lambda x : self.promotion_on_highest_weight_vectors()[x]955956def promotion(self):957"""958Specifies the promotion operator used to construct the affine type `E_6^{(1)}` crystal.959960EXAMPLES::961962sage: K = KirillovReshetikhinCrystal(['E',6,1], 2,1)963sage: promotion = K.promotion()964sage: all(promotion(promotion(promotion(b))) == b for b in K.classical_decomposition())965True966sage: K = KirillovReshetikhinCrystal(['E',6,1],1,1)967sage: promotion = K.promotion()968sage: all(promotion(promotion(promotion(b))) == b for b in K.classical_decomposition())969True970"""971T = self.classical_decomposition()972ind = [1,2,3,4,5]973return T.crystal_morphism( self.promotion_on_highest_weight_vectors_function(), automorphism = lambda i : self.dynkin_diagram_automorphism(i), index_set = ind)974975def promotion_inverse(self):976r"""977Returns the inverse promotion. Since promotion is of order 3, the inverse promotion is the same978as promotion applied twice.979980EXAMPLES::981982sage: K = KirillovReshetikhinCrystal(['E',6,1], 2,1)983sage: p = K.promotion()984sage: p_inv = K.promotion_inverse()985sage: all(p_inv(p(b)) == b for b in K.classical_decomposition())986True987"""988p = self.promotion()989return lambda x : p(p(x))990991992class KR_type_C(KirillovReshetikhinGenericCrystal, AffineCrystalFromClassical):993r"""994Class of Kirillov-Reshetikhin crystals `B^{r,s}` of type `C_n^{(1)}` for `r<n`.995996EXAMPLES::997998sage: K = KirillovReshetikhinCrystal(['C',2,1], 1,2)999sage: K1000Kirillov-Reshetikhin crystal of type ['C', 2, 1] with (r,s)=(1,2)1001sage: b = K(rows=[])1002sage: b.f(0)1003[[1, 1]]1004sage: b.e(0)1005[[-1, -1]]1006"""1007def __init__(self, cartan_type, r, s):1008r"""1009Initializes a Kirillov-Reshetikhin crystal of type `C_n^{(1)}`.10101011TESTS::10121013sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_C(['C',2,1], 1, 1)1014sage: K1015Kirillov-Reshetikhin crystal of type ['C', 2, 1] with (r,s)=(1,1)1016sage: TestSuite(K).run()1017"""1018KirillovReshetikhinGenericCrystal.__init__(self, cartan_type, r ,s)1019AffineCrystalFromClassical.__init__(self, cartan_type, self.classical_decomposition())10201021def classical_decomposition(self):1022"""1023Specifies the classical crystal underlying the Kirillov-Reshetikhin crystal of type `C_n^{(1)}`.1024It is given by `B^{r,s} \cong \oplus_\Lambda B(\Lambda)` where `\Lambda` are weights obtained from1025a rectangle of width s and height r by removing horizontal dominoes. Here we identify the fundamental1026weight `\Lambda_i` with a column of height `i`.10271028EXAMPLES::10291030sage: K = KirillovReshetikhinCrystal(['C',3,1], 2,2)1031sage: K.classical_decomposition()1032The crystal of tableaux of type ['C', 3] and shape(s) [[], [2], [2, 2]]1033"""1034return CrystalOfTableaux(self.cartan_type().classical(),1035shapes = horizontal_dominoes_removed(self.r(),self.s()))10361037def ambient_crystal(self):1038r"""1039Returns the ambient crystal `'B^{r,s}` of type `A_{2n+1}^{(2)}` associated to the Kirillov-Reshetikhin1040crystal of type `C_n^{(1)}`. This ambient crystal is used to construct the zero arrows.10411042EXAMPLES::10431044sage: K = KirillovReshetikhinCrystal(['C',3,1], 2,3)1045sage: K.ambient_crystal()1046Kirillov-Reshetikhin crystal of type ['B', 4, 1]^* with (r,s)=(2,3)1047"""1048return KirillovReshetikhinCrystal(['A',2*self.cartan_type().classical().rank()+1,2], self.r(), self.s())10491050def ambient_dict_pm_diagrams(self):1051r"""1052Gives a dictionary of all self-dual `\pm` diagrams for the ambient crystal.1053Their key is their inner shape.10541055EXAMPLES::10561057sage: K = KirillovReshetikhinCrystal(['C',2,1], 1,2)1058sage: K.ambient_dict_pm_diagrams()1059{[]: [[1, 1], [0]], [2]: [[0, 0], [2]]}1060sage: K = KirillovReshetikhinCrystal(['C',3,1], 2,2)1061sage: K.ambient_dict_pm_diagrams()1062{[2, 2]: [[0, 0], [0, 0], [2]], []: [[1, 1], [0, 0], [0]], [2]: [[0, 0], [1, 1], [0]]}1063sage: K = KirillovReshetikhinCrystal(['C',3,1], 2,3)1064sage: K.ambient_dict_pm_diagrams()1065{[3, 3]: [[0, 0], [0, 0], [3]], [3, 1]: [[0, 0], [1, 1], [1]], [1, 1]: [[1, 1], [0, 0], [1]]}1066"""1067list = []1068s = self.s()1069r = self.r()1070m = int(s/2)1071for i in range(m+1):1072for la in IntegerVectors(m-i, min_length=r, max_length=r):1073list.append(PMDiagram([[j,j] for j in la]+[[s-2*m+2*i]]))1074return dict( (x.inner_shape(), x) for x in list )10751076def ambient_highest_weight_dict(self):1077r"""1078Gives a dictionary of all `{2,...,n+1}`-highest weight vectors in the ambient crystal.1079Their key is the inner shape of their corresponding `\pm` diagram, or equivalently, their1080`{2,...,n+1}` weight.10811082EXAMPLES::10831084sage: K = KirillovReshetikhinCrystal(['C',3,1], 2,2)1085sage: K.ambient_highest_weight_dict()1086{[]: [[2], [-2]], [2, 2]: [[2, 2], [3, 3]], [2]: [[1, 2], [2, -1]]}1087"""1088A = self.ambient_dict_pm_diagrams()1089ambient = self.ambient_crystal()1090return dict( (key, ambient.retract(ambient.from_pm_diagram_to_highest_weight_vector(A[key]))) for key in A )10911092def highest_weight_dict(self):1093r"""1094Gives a dictionary of the classical highest weight vectors of self.1095Their key is their shape.10961097EXAMPLES::10981099sage: K = KirillovReshetikhinCrystal(['C',3,1], 2,2)1100sage: K.highest_weight_dict()1101{[2, 2]: [[1, 1], [2, 2]], []: [], [2]: [[1, 1]]}1102"""1103return dict( (x.lift().to_tableau().shape(),x) for x in self.module_generators )11041105def to_ambient_crystal(self):1106r"""1107Provides a map from the Kirillov-Reshetikhin crystal of type `C_n^{(1)}` to the1108ambient crystal of type `A_{2n+1}^{(2)}`.11091110EXAMPLES::11111112sage: K = KirillovReshetikhinCrystal(['C',3,1], 2,2)1113sage: b=K(rows=[[1,1]])1114sage: K.to_ambient_crystal()(b)1115[[1, 2], [2, -1]]1116sage: b=K(rows=[])1117sage: K.to_ambient_crystal()(b)1118[[2], [-2]]1119sage: K.to_ambient_crystal()(b).parent() # Anne: please check this!!!!1120Kirillov-Reshetikhin crystal of type ['B', 4, 1]^* with (r,s)=(2,2)1121"""1122keys = self.highest_weight_dict().keys()1123pdict = dict( (self.highest_weight_dict()[key], self.ambient_highest_weight_dict()[key]) for key in keys )1124return self.crystal_morphism( pdict, index_set = self.cartan_type().classical().index_set(),1125automorphism = lambda i : i+1 )11261127def from_ambient_crystal(self):1128r"""1129Provides a map from the ambient crystal of type `A_{2n+1}^{(2)}` to the Kirillov-Reshetikhin crystal of1130type `C_n^{(1)}`. Note that this map is only well-defined on elements that are in the image1131type `C_n^{(1)}` elements under `to_ambient_crystal`.11321133EXAMPLES::11341135sage: K = KirillovReshetikhinCrystal(['C',3,1], 2,2)1136sage: b=K.ambient_crystal()(rows=[[2,2],[3,3]])1137sage: K.from_ambient_crystal()(b)1138[[1, 1], [2, 2]]1139"""1140keys = self.highest_weight_dict().keys()1141pdict_inv = dict( (self.ambient_highest_weight_dict()[key], self.highest_weight_dict()[key]) for key in keys )1142return self.crystal_morphism( pdict_inv, index_set = [j+1 for j in self.cartan_type().classical().index_set()],1143automorphism = lambda i : i-1 )11441145class KR_type_CElement(AffineCrystalFromClassicalElement):1146r"""1147Class for the elements in the Kirillov-Reshetikhin crystals `B^{r,s}` of type `C_n^{(1)}` for `r<n`.11481149EXAMPLES::11501151sage: K=KirillovReshetikhinCrystal(['C',3,1],1,2)1152sage: type(K.module_generators[0])1153<class 'sage.combinat.crystals.kirillov_reshetikhin.KR_type_C_with_category.element_class'>1154"""11551156def e0(self):1157r"""1158Gives `e_0` on self by mapping self to the ambient crystal, calculating `e_1 e_0` there and1159pulling the element back.11601161EXAMPLES::11621163sage: K=KirillovReshetikhinCrystal(['C',3,1],1,2)1164sage: b = K(rows=[])1165sage: b.e(0)1166[[-1, -1]]1167"""1168b = self.parent().to_ambient_crystal()(self).e(1)1169if b is None:1170return None1171b = b.e(0)1172return self.parent().from_ambient_crystal()(b)11731174def f0(self):1175r"""1176Gives `f_0` on self by mapping self to the ambient crystal, calculating `f_1 f_0` there and1177pulling the element back.11781179EXAMPLES::11801181sage: K=KirillovReshetikhinCrystal(['C',3,1],1,2)1182sage: b = K(rows=[])1183sage: b.f(0)1184[[1, 1]]1185"""1186b = self.parent().to_ambient_crystal()(self).f(1)1187if b is None:1188return None1189b = b.f(0)1190return self.parent().from_ambient_crystal()(b)11911192def epsilon0(self):1193r"""1194Calculates `\epsilon_0` of self by mapping the element to the ambient crystal1195and calculating `\epsilon_1` there.11961197EXAMPLES::11981199sage: K = KirillovReshetikhinCrystal(['C',2,1], 1,2)1200sage: b=K(rows=[[1,1]])1201sage: b.epsilon(0)120221203"""1204b = self.parent().to_ambient_crystal()(self)1205return b.epsilon(1)12061207def phi0(self):1208r"""1209Calculates `\phi_0` of self by mapping the element to the ambient crystal1210and calculating `\phi_1` there.12111212EXAMPLES::12131214sage: K = KirillovReshetikhinCrystal(['C',2,1], 1,2)1215sage: b=K(rows=[[-1,-1]])1216sage: b.phi(0)121721218"""1219b = self.parent().to_ambient_crystal()(self)1220return b.phi(1)12211222KR_type_C.Element = KR_type_CElement122312241225class KR_type_A2(KirillovReshetikhinGenericCrystal, AffineCrystalFromClassical):1226r"""1227Class of Kirillov-Reshetikhin crystals `B^{r,s}` of type `A_{2n}^{(2)}` for `1\le r \le n`1228in the realization with classical subalgebra `B_n`. The cartan type in this case is inputted as1229the dual of `A_{2n}^{(2)}`.1230This is an alternative implementation to KR_type_box which uses the classical decomposition1231into type `C_n` crystals.12321233EXAMPLES::12341235sage: C = CartanType(['A',4,2]).dual()1236sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 1, 1)1237sage: K1238Kirillov-Reshetikhin crystal of type ['BC', 2, 2]^* with (r,s)=(1,1)1239sage: b = K(rows=[[-1]])1240sage: b.f(0)1241[[1]]1242sage: b.e(0)12431244We can now check whether the two KR crystals of type `A_4^{(2)}` (namely the KR crystal and its dual1245construction) are isomorphic up to relabelling of the edges::12461247sage: C = CartanType(['A',4,2])1248sage: K = KirillovReshetikhinCrystal(C,1,1)1249sage: Kdual = KirillovReshetikhinCrystal(C.dual(),1,1)1250sage: G = K.digraph()1251sage: Gdual = Kdual.digraph()1252sage: f = {0:2, 1:1, 2:0}1253sage: Gnew = DiGraph(); Gnew.add_vertices(Gdual.vertices()); Gnew.add_edges([(u,v,f[i]) for (u,v,i) in Gdual.edges()])1254sage: G.is_isomorphic(Gnew, edge_labels = True)1255True1256"""1257def __init__(self, cartan_type, r, s):1258r"""1259Initializes a Kirillov-Reshetikhin crystal of type `A_{2n}^{(2)}` in the realization1260with classical subalgebra `B_n`.12611262TESTS::12631264sage: C = CartanType(['A',4,2]).dual()1265sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 1, 1)1266sage: K1267Kirillov-Reshetikhin crystal of type ['BC', 2, 2]^* with (r,s)=(1,1)1268sage: TestSuite(K).run()1269"""1270KirillovReshetikhinGenericCrystal.__init__(self, cartan_type, r ,s)1271AffineCrystalFromClassical.__init__(self, cartan_type, self.classical_decomposition())12721273def classical_decomposition(self):1274"""1275Specifies the classical crystal underlying the Kirillov-Reshetikhin crystal of type `A_{2n}^{(2)}`1276with `B_n` as classical subdiagram.1277It is given by `B^{r,s} \cong \oplus_\Lambda B(\Lambda)` where `B(\Lambda)` is a highest weight crystal of type1278`B_n` of highest weight `\Lambda`. The sum is over all weights `Lambda` obtained from1279a rectangle of width s and height r by removing horizontal dominoes. Here we identify the fundamental1280weight `\Lambda_i` with a column of height `i`.12811282EXAMPLES::12831284sage: C = CartanType(['A',4,2]).dual()1285sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 2, 2)1286sage: K.classical_decomposition()1287The crystal of tableaux of type ['B', 2] and shape(s) [[], [2], [2, 2]]1288"""1289return CrystalOfTableaux(['B', self.cartan_type().rank()-1],1290shapes = horizontal_dominoes_removed(self.r(),self.s()))12911292def ambient_crystal(self):1293r"""1294Returns the ambient crystal `'B^{r,s}` of type `B_{n+1}^{(1)}` associated to the Kirillov-Reshetikhin1295crystal of type `A_{2n}^{(2)}` dual. This ambient crystal is used to construct the zero arrows.12961297EXAMPLES::12981299sage: C = CartanType(['A',4,2]).dual()1300sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 2, 3)1301sage: K.ambient_crystal()1302Kirillov-Reshetikhin crystal of type ['B', 3, 1] with (r,s)=(2,3)1303"""1304return KR_type_vertical(['B', self.cartan_type().rank(), 1], self.r(), self.s())13051306def ambient_dict_pm_diagrams(self):1307r"""1308Gives a dictionary of all self-dual `\pm` diagrams for the ambient crystal.1309Their key is their inner shape.13101311EXAMPLES::13121313sage: C = CartanType(['A',4,2]).dual()1314sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 1, 1)1315sage: K.ambient_dict_pm_diagrams()1316{[1]: [[0, 0], [1]]}1317sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 1, 2)1318sage: K.ambient_dict_pm_diagrams()1319{[]: [[1, 1], [0]], [2]: [[0, 0], [2]]}1320sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 2, 2)1321sage: K.ambient_dict_pm_diagrams()1322{[2, 2]: [[0, 0], [0, 0], [2]], []: [[1, 1], [0, 0], [0]], [2]: [[0, 0], [1, 1], [0]]}1323"""1324list = []1325s = self.s()1326r = self.r()1327m = int(s/2)1328for i in range(m+1):1329for la in IntegerVectors(m-i, min_length=r, max_length=r):1330list.append(PMDiagram([[j,j] for j in la]+[[s-2*m+2*i]]))1331return dict( (x.inner_shape(), x) for x in list )13321333def ambient_highest_weight_dict(self):1334r"""1335Gives a dictionary of all `{2,...,n+1}`-highest weight vectors in the ambient crystal.1336Their key is the inner shape of their corresponding `\pm` diagram, or equivalently, their1337`{2,...,n+1}` weight.13381339EXAMPLES::13401341sage: C = CartanType(['A',4,2]).dual()1342sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 1, 2)1343sage: K.ambient_highest_weight_dict()1344{[]: [[1, -1]], [2]: [[2, 2]]}1345"""1346A = self.ambient_dict_pm_diagrams()1347ambient = self.ambient_crystal()1348return dict( (key, ambient.retract(ambient.from_pm_diagram_to_highest_weight_vector(A[key]))) for key in A )13491350def highest_weight_dict(self):1351r"""1352Gives a dictionary of the classical highest weight vectors of self.1353Their key is their shape.13541355EXAMPLES::13561357sage: C = CartanType(['A',4,2]).dual()1358sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 1, 2)1359sage: K.highest_weight_dict()1360{[]: [], [2]: [[1, 1]]}1361"""1362return dict( (x.lift().to_tableau().shape(),x) for x in self.module_generators )13631364def to_ambient_crystal(self):1365r"""1366Provides a map from the Kirillov-Reshetikhin crystal of type `A_{2n}^{(2)}` to the1367ambient crystal of type `B_{n+1}^{(1)}`.13681369EXAMPLES::13701371sage: C = CartanType(['A',4,2]).dual()1372sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 1, 2)1373sage: b=K(rows=[[1,1]])1374sage: K.to_ambient_crystal()(b)1375[[2, 2]]1376sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 2, 2)1377sage: b=K(rows=[[1,1]])1378sage: K.to_ambient_crystal()(b)1379[[1, 2], [2, -1]]1380sage: K.to_ambient_crystal()(b).parent()1381Kirillov-Reshetikhin crystal of type ['B', 3, 1] with (r,s)=(2,2)1382"""1383keys = self.highest_weight_dict().keys()1384pdict = dict( (self.highest_weight_dict()[key], self.ambient_highest_weight_dict()[key]) for key in keys )1385return self.crystal_morphism( pdict, index_set = self.cartan_type().classical().index_set(),1386automorphism = lambda i : i+1 )13871388def from_ambient_crystal(self):1389r"""1390Provides a map from the ambient crystal of type `B_{n+1}^{(1)}` to the Kirillov-Reshetikhin crystal of1391type `A_{2n}^{(2)}`. Note that this map is only well-defined on elements that are in the image1392type `A_{2n}^{(2)}` elements under `to_ambient_crystal`.13931394EXAMPLES::13951396sage: C = CartanType(['A',4,2]).dual()1397sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 1, 2)1398sage: b = K.ambient_crystal()(rows=[[2,2]])1399sage: K.from_ambient_crystal()(b)1400[[1, 1]]1401"""1402keys = self.highest_weight_dict().keys()1403pdict_inv = dict( (self.ambient_highest_weight_dict()[key], self.highest_weight_dict()[key]) for key in keys )1404return self.crystal_morphism( pdict_inv, index_set = [j+1 for j in self.cartan_type().classical().index_set()],1405automorphism = lambda i : i-1 )14061407class KR_type_A2Element(AffineCrystalFromClassicalElement):1408r"""1409Class for the elements in the Kirillov-Reshetikhin crystals `B^{r,s}` of type `A_{2n}^{(2)}` for `r<n`1410with underlying classcial algebra `B_n`.14111412EXAMPLES::14131414sage: C = CartanType(['A',4,2]).dual()1415sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 1, 2)1416sage: type(K.module_generators[0])1417<class 'sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2_with_category.element_class'>1418"""14191420def e0(self):1421r"""1422Gives `e_0` on self by mapping self to the ambient crystal, calculating `e_1 e_0` there and1423pulling the element back.14241425EXAMPLES::14261427sage: C = CartanType(['A',4,2]).dual()1428sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 1, 1)1429sage: b = K(rows=[[1]])1430sage: b.e(0)1431[[-1]]1432"""1433b = self.parent().to_ambient_crystal()(self).e(1)1434if b is None:1435return None1436b = b.e(0)1437return self.parent().from_ambient_crystal()(b)14381439def f0(self):1440r"""1441Gives `f_0` on self by mapping self to the ambient crystal, calculating `f_1 f_0` there and1442pulling the element back.14431444EXAMPLES::14451446sage: C = CartanType(['A',4,2]).dual()1447sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 1, 1)1448sage: b = K(rows=[[-1]])1449sage: b.f(0)1450[[1]]1451"""1452b = self.parent().to_ambient_crystal()(self).f(1)1453if b is None:1454return None1455b = b.f(0)1456return self.parent().from_ambient_crystal()(b)14571458def epsilon0(self):1459r"""1460Calculates `\epsilon_0` of self by mapping the element to the ambient crystal1461and calculating `\epsilon_1` there.14621463EXAMPLES::14641465sage: C = CartanType(['A',4,2]).dual()1466sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 1, 1)1467sage: b=K(rows=[[1]])1468sage: b.epsilon(0)146911470"""1471b = self.parent().to_ambient_crystal()(self)1472return b.epsilon(1)14731474def phi0(self):1475r"""1476Calculates `\phi_0` of self by mapping the element to the ambient crystal1477and calculating `\phi_1` there.14781479EXAMPLES::14801481sage: C = CartanType(['A',4,2]).dual()1482sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_A2(C, 1, 1)1483sage: b=K(rows=[[-1]])1484sage: b.phi(0)148511486"""1487b = self.parent().to_ambient_crystal()(self)1488return b.phi(1)14891490KR_type_A2.Element = KR_type_A2Element149114921493class KR_type_box(KirillovReshetikhinGenericCrystal, AffineCrystalFromClassical):1494r"""1495Class of Kirillov-Reshetikhin crystals `B^{r,s}` of type `A_{2n}^{(2)}` for `r\le n`1496and type `D_{n+1}^{(2)}` for `r<n`.14971498EXAMPLES::14991500sage: K = KirillovReshetikhinCrystal(['A',4,2], 1,1)1501sage: K1502Kirillov-Reshetikhin crystal of type ['BC', 2, 2] with (r,s)=(1,1)1503sage: b = K(rows=[])1504sage: b.f(0)1505[[1]]1506sage: b.e(0)1507[[-1]]1508"""1509def __init__(self, cartan_type, r, s):1510r"""1511Initializes a Kirillov-Reshetikhin crystal ``self``.15121513TESTS::15141515sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_box(['A',4,2], 1, 1)1516sage: K1517Kirillov-Reshetikhin crystal of type ['BC', 2, 2] with (r,s)=(1,1)1518sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_box(['D',4,2], 1, 1)1519sage: K1520Kirillov-Reshetikhin crystal of type ['C', 3, 1]^* with (r,s)=(1,1)1521sage: TestSuite(K).run()1522"""1523KirillovReshetikhinGenericCrystal.__init__(self, cartan_type, r ,s)1524AffineCrystalFromClassical.__init__(self, cartan_type, self.classical_decomposition())15251526def classical_decomposition(self):1527r"""1528Specifies the classical crystal underlying the Kirillov-Reshetikhin crystal of type `A_{2n}^{(2)}`1529and `D_{n+1}^{(2)}`.1530It is given by `B^{r,s} \cong \oplus_\Lambda B(\Lambda)` where `\Lambda` are weights obtained from1531a rectangle of width s and height r by removing boxes. Here we identify the fundamental1532weight `\Lambda_i` with a column of height `i`.15331534EXAMPLES::15351536sage: K = KirillovReshetikhinCrystal(['A',4,2], 2,2)1537sage: K.classical_decomposition()1538The crystal of tableaux of type ['C', 2] and shape(s) [[], [1], [2], [1, 1], [2, 1], [2, 2]]1539sage: K = KirillovReshetikhinCrystal(['D',4,2], 2,3)1540sage: K.classical_decomposition()1541The crystal of tableaux of type ['B', 3] and shape(s) [[], [1], [2], [1, 1], [3], [2, 1], [3, 1], [2, 2], [3, 2], [3, 3]]1542"""1543return CrystalOfTableaux(self.cartan_type().classical(),1544shapes = partitions_in_box(self.r(),self.s()))15451546def ambient_crystal(self):1547r"""1548Returns the ambient crystal `'B^{r,2s}` of type `C_n^{(1)}` associated to the Kirillov-Reshetikhin crystal.1549This ambient crystal is used to construct the zero arrows.15501551EXAMPLES::15521553sage: K = KirillovReshetikhinCrystal(['A',4,2], 2,2)1554sage: K.ambient_crystal()1555Kirillov-Reshetikhin crystal of type ['C', 2, 1] with (r,s)=(2,4)1556"""1557# calling KR_type_C instead of KirillovReshetikhin(['C',n,1],r,s) has the advantage that1558# that this also works for r=n for A_{2n}^{(2)}.1559return KR_type_C(['C', self.cartan_type().classical().rank(),1], self.r(), 2*self.s())15601561def highest_weight_dict(self):1562r"""1563Gives a dictionary of the classical highest weight vectors of self.1564Their key is 2 times their shape.15651566EXAMPLES::15671568sage: K = KirillovReshetikhinCrystal(['A',6,2], 2,2)1569sage: K.highest_weight_dict()1570{[4, 2]: [[1, 1], [2]], [2, 2]: [[1], [2]], []: [], [4]: [[1, 1]], [4, 4]: [[1, 1], [2, 2]], [2]: [[1]]}1571"""1572return dict( (Partition([2*i for i in x.lift().to_tableau().shape()]),x) for x in self.module_generators )15731574def ambient_highest_weight_dict(self):1575r"""1576Gives a dictionary of the classical highest weight vectors of the ambient crystal of self.1577Their key is their shape.15781579EXAMPLES::15801581sage: K = KirillovReshetikhinCrystal(['A',6,2], 2,2)1582sage: K.ambient_highest_weight_dict()1583{[4, 2]: [[1, 1, 1, 1], [2, 2]], [2, 2]: [[1, 1], [2, 2]], []: [], [4]: [[1, 1, 1, 1]], [4, 4]: [[1, 1, 1, 1], [2, 2, 2, 2]],1584[2]: [[1, 1]]}1585"""1586return dict( (x.lift().to_tableau().shape(),x) for x in self.ambient_crystal().module_generators )15871588def similarity_factor(self):1589r"""1590Sets the similarity factor used to map to the ambient crystal.15911592EXAMPLES::15931594sage: K = KirillovReshetikhinCrystal(['A',6,2], 2,2)1595sage: K.similarity_factor()1596{1: 2, 2: 2, 3: 2}1597sage: K = KirillovReshetikhinCrystal(['D',5,2], 1,1)1598sage: K.similarity_factor()1599{1: 2, 2: 2, 3: 2, 4: 1}1600"""1601C = self.cartan_type().classical()1602p = dict( (i,2) for i in C.index_set() )1603if C.type() == 'B':1604p[C.rank()] = 11605return p16061607def to_ambient_crystal(self):1608r"""1609Provides a map from self to the ambient crystal of type `C_n^{(1)}`.16101611EXAMPLES::16121613sage: K = KirillovReshetikhinCrystal(['D',4,2], 1,1)1614sage: [K.to_ambient_crystal()(b) for b in K]1615[[], [[1, 1]], [[2, 2]], [[3, 3]], [[3, -3]], [[-3, -3]], [[-2, -2]], [[-1, -1]]]1616sage: K = KirillovReshetikhinCrystal(['A',4,2], 1,1)1617sage: [K.to_ambient_crystal()(b) for b in K]1618[[], [[1, 1]], [[2, 2]], [[-2, -2]], [[-1, -1]]]1619"""1620keys = self.highest_weight_dict().keys()1621pdict = dict( (self.highest_weight_dict()[key], self.ambient_highest_weight_dict()[key]) for key in keys )1622return self.crystal_morphism( pdict, index_set = self.cartan_type().classical().index_set(),1623similarity_factor = self.similarity_factor() )16241625def from_ambient_crystal(self):1626r"""1627Provides a map from the ambient crystal of type `C_n^{(1)}` to the Kirillov-Reshetikhin crystal self.1628Note that this map is only well-defined on elements that are in the image under `to_ambient_crystal`.16291630EXAMPLES::16311632sage: K = KirillovReshetikhinCrystal(['D',4,2], 1,1)1633sage: b = K.ambient_crystal()(rows=[[3,-3]])1634sage: K.from_ambient_crystal()(b)1635[[0]]1636sage: K = KirillovReshetikhinCrystal(['A',4,2], 1,1)1637sage: b = K.ambient_crystal()(rows=[])1638sage: K.from_ambient_crystal()(b)1639[]1640"""1641keys = self.highest_weight_dict().keys()1642pdict_inv = dict( (self.ambient_highest_weight_dict()[key], self.highest_weight_dict()[key]) for key in keys )1643return self.crystal_morphism( pdict_inv, index_set = self.cartan_type().classical().index_set(),1644similarity_factor_domain = self.similarity_factor() )164516461647class KR_type_boxElement(AffineCrystalFromClassicalElement):1648r"""1649Class for the elements in the Kirillov-Reshetikhin crystals `B^{r,s}` of type `A_{2n}^{(2)}` for `r\le n`1650and type `D_{n+1}^{(2)}` for `r<n`.16511652EXAMPLES::16531654sage: K=KirillovReshetikhinCrystal(['A',4,2],1,2)1655sage: type(K.module_generators[0])1656<class 'sage.combinat.crystals.kirillov_reshetikhin.KR_type_box_with_category.element_class'>1657"""16581659def e0(self):1660r"""1661Gives `e_0` on self by mapping self to the ambient crystal, calculating `e_0` there and1662pulling the element back.16631664EXAMPLES::16651666sage: K=KirillovReshetikhinCrystal(['A',4,2],1,1)1667sage: b = K(rows=[])1668sage: b.e(0)1669[[-1]]1670"""1671b = self.parent().to_ambient_crystal()(self).e(0)1672if b is None:1673return None1674return self.parent().from_ambient_crystal()(b)16751676def f0(self):1677r"""1678Gives `f_0` on self by mapping self to the ambient crystal, calculating `f_0` there and1679pulling the element back.16801681EXAMPLES::16821683sage: K=KirillovReshetikhinCrystal(['A',4,2],1,1)1684sage: b = K(rows=[])1685sage: b.f(0)1686[[1]]1687"""1688b = self.parent().to_ambient_crystal()(self).f(0)1689if b is None:1690return None1691return self.parent().from_ambient_crystal()(b)16921693def epsilon0(self):1694r"""1695Calculates `\epsilon_0` of self by mapping the element to the ambient crystal1696and calculating `\epsilon_0` there.16971698EXAMPLES::16991700sage: K = KirillovReshetikhinCrystal(['A',4,2], 1,1)1701sage: b=K(rows=[[1]])1702sage: b.epsilon(0)170321704"""1705b = self.parent().to_ambient_crystal()(self)1706return b.epsilon(0)17071708def phi0(self):1709r"""1710Calculates `\phi_0` of self by mapping the element to the ambient crystal1711and calculating `\phi_0` there.17121713EXAMPLES::17141715sage: K = KirillovReshetikhinCrystal(['D',3,2], 1,1)1716sage: b=K(rows=[[-1]])1717sage: b.phi(0)171821719"""1720b = self.parent().to_ambient_crystal()(self)1721return b.phi(0)17221723KR_type_box.Element = KR_type_boxElement172417251726class KR_type_Bn(KirillovReshetikhinGenericCrystal, AffineCrystalFromClassical):1727r"""1728Class of Kirillov-Reshetikhin crystals `B^{n,s}` of type `B_{n}^{(1)}`.17291730EXAMPLES::17311732sage: K = KirillovReshetikhinCrystal(['B',3,1],3,2)1733sage: K1734Kirillov-Reshetikhin crystal of type ['B', 3, 1] with (r,s)=(3,2)1735sage: b = K(rows=[[1],[2],[3]])1736sage: b.f(0)1737sage: b.e(0)1738[[3]]17391740sage: K = KirillovReshetikhinCrystal(['B',3,1],3,2)1741sage: [b.weight() for b in K if b.is_highest_weight([1,2,3])]1742[-Lambda[0] + Lambda[1], -2*Lambda[0] + 2*Lambda[3]]1743sage: [b.weight() for b in K if b.is_highest_weight([0,2,3])]1744[Lambda[0] - Lambda[1], -2*Lambda[1] + 2*Lambda[3]]1745"""17461747def __init__(self, cartan_type, r, s):1748r"""1749Initializes a Kirillov-Reshetikhin crystal ``self``.17501751TESTS::17521753sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_Bn(['B',3,1], 3, 1)1754sage: K1755Kirillov-Reshetikhin crystal of type ['B', 3, 1] with (r,s)=(3,1)1756sage: TestSuite(K).run()1757"""1758KirillovReshetikhinGenericCrystal.__init__(self, cartan_type, r ,s)1759AffineCrystalFromClassical.__init__(self, cartan_type, self.classical_decomposition())17601761def classical_decomposition(self):1762r"""1763Specifies the classical crystal underlying the Kirillov-Reshetikhin crystal `B^{n,s}` of type `B_n^{(1)}`.1764It is the same as for `r<n`, given by `B^{n,s} \cong \oplus_\Lambda B(\Lambda)` where `\Lambda` are1765weights obtained from a rectangle of width `s/2` and height `n` by removing horizontal dominoes.1766Here we identify the fundamental weight `\Lambda_i` with a column of height `i` for `i<n` and1767a column of width `1/2` for `i=n`.17681769EXAMPLES::17701771sage: K = KirillovReshetikhinCrystal(['B',3,1], 3, 2)1772sage: K.classical_decomposition()1773The crystal of tableaux of type ['B', 3] and shape(s) [[1], [1, 1, 1]]1774sage: K = KirillovReshetikhinCrystal(['B',3,1], 3, 3)1775sage: K.classical_decomposition()1776The crystal of tableaux of type ['B', 3] and shape(s) [[3/2, 1/2, 1/2], [3/2, 3/2, 3/2]]1777"""1778s = self.s()1779r = self.r()1780shapes = vertical_dominoes_removed(r,floor(s/2))1781if is_odd(s):1782shapes = [ [i+QQ(1)/QQ(2) for i in sh]+[QQ(1)/QQ(2)]*(r-len(sh)) for sh in shapes ]1783return CrystalOfTableaux(self.cartan_type().classical(), shapes = shapes)17841785def ambient_crystal(self):1786r"""1787Returns the ambient crystal `'B^{n,s}` of type `A_{2n-1}^{(2)}` associated to the Kirillov-Reshetikhin crystal;1788see Lemma 4.2 of reference [4].1789This ambient crystal is used to construct the zero arrows.17901791EXAMPLES::17921793sage: K = KirillovReshetikhinCrystal(['B',3,1],3,2)1794sage: K.ambient_crystal()1795Kirillov-Reshetikhin crystal of type ['B', 3, 1]^* with (r,s)=(3,2)1796"""1797return KirillovReshetikhinCrystal(['A', 2*self.cartan_type().classical().rank()-1,2], self.r(), self.s())17981799def highest_weight_dict(self):1800r"""1801Gives a dictionary of the classical highest weight vectors of self.1802Their key is 2 times their shape.18031804EXAMPLES::18051806sage: K = KirillovReshetikhinCrystal(['B',3,1],3,2)1807sage: K.highest_weight_dict()1808{(2,): [[1]], (2, 2, 2): [[1], [2], [3]]}1809sage: K = KirillovReshetikhinCrystal(['B',3,1],3,3)1810sage: K.highest_weight_dict()1811{(3, 3, 3): [+++, [[1], [2], [3]]], (3, 1, 1): [+++, [[1]]]}1812"""1813return dict( (tuple([2*i[1] for i in x.classical_weight()]),x) for x in self.module_generators )18141815def ambient_highest_weight_dict(self):1816r"""1817Gives a dictionary of the classical highest weight vectors of the ambient crystal of self.1818Their key is their shape.18191820EXAMPLES::18211822sage: K = KirillovReshetikhinCrystal(['B',3,1],3,2)1823sage: K.ambient_highest_weight_dict()1824{(2,): [[1, 1]], (2, 1, 1): [[1, 1], [2], [3]], (2, 2, 2): [[1, 1], [2, 2], [3, 3]]}18251826sage: K = KirillovReshetikhinCrystal(['B',3,1],3,3)1827sage: K.ambient_highest_weight_dict()1828{(3, 3, 3): [[1, 1, 1], [2, 2, 2], [3, 3, 3]], (3, 1, 1): [[1, 1, 1], [2], [3]],1829(3, 2, 2): [[1, 1, 1], [2, 2], [3, 3]], (3,): [[1, 1, 1]]}1830"""1831return dict( (tuple([i[1] for i in x.classical_weight()]),x) for x in self.ambient_crystal().module_generators )18321833def similarity_factor(self):1834r"""1835Sets the similarity factor used to map to the ambient crystal.18361837EXAMPLES::18381839sage: K = KirillovReshetikhinCrystal(['B',3,1],3,2)1840sage: K.similarity_factor()1841{1: 2, 2: 2, 3: 1}1842"""1843C = self.cartan_type().classical()1844p = dict( (i,2) for i in C.index_set() )1845p[C.rank()] = 11846return p18471848def to_ambient_crystal(self):1849r"""1850Provides a map from self to the ambient crystal of type `A_{2n-1}^{(2)}`.18511852EXAMPLES::18531854sage: K = KirillovReshetikhinCrystal(['B',3,1],3,1)1855sage: [K.to_ambient_crystal()(b) for b in K]1856[[[1], [2], [3]], [[1], [2], [-3]], [[1], [3], [-2]], [[2], [3], [-1]], [[1], [-3], [-2]],1857[[2], [-3], [-1]], [[3], [-2], [-1]], [[-3], [-2], [-1]]]1858"""1859keys = self.highest_weight_dict().keys()1860pdict = dict( (self.highest_weight_dict()[key], self.ambient_highest_weight_dict()[key]) for key in keys )1861return self.crystal_morphism( pdict, index_set = self.cartan_type().classical().index_set(),1862similarity_factor = self.similarity_factor() )18631864def from_ambient_crystal(self):1865r"""1866Provides a map from the ambient crystal of type `A_{2n-1}^{(2)}` to the Kirillov-Reshetikhin crystal self.1867Note that this map is only well-defined on elements that are in the image under `to_ambient_crystal`.18681869EXAMPLES::18701871sage: K = KirillovReshetikhinCrystal(['B',3,1],3,1)1872sage: [b == K.from_ambient_crystal()(K.to_ambient_crystal()(b)) for b in K]1873[True, True, True, True, True, True, True, True]1874sage: b = K.ambient_crystal()(rows=[[1],[2],[-3]])1875sage: K.from_ambient_crystal()(b)1876[++-, []]1877"""1878keys = self.highest_weight_dict().keys()1879pdict_inv = dict( (self.ambient_highest_weight_dict()[key], self.highest_weight_dict()[key]) for key in keys )1880return self.crystal_morphism( pdict_inv, index_set = self.cartan_type().classical().index_set(),1881similarity_factor_domain = self.similarity_factor() )188218831884class KR_type_BnElement(AffineCrystalFromClassicalElement):1885r"""1886Class for the elements in the Kirillov-Reshetikhin crystals `B^{n,s}` of type `B_n^{(1)}`.18871888EXAMPLES::18891890sage: K=KirillovReshetikhinCrystal(['B',3,1],3,2)1891sage: type(K.module_generators[0])1892<class 'sage.combinat.crystals.kirillov_reshetikhin.KR_type_Bn_with_category.element_class'>1893"""18941895def e0(self):1896r"""1897Gives `e_0` on self by mapping self to the ambient crystal, calculating `e_0` there and1898pulling the element back.18991900EXAMPLES::19011902sage: K=KirillovReshetikhinCrystal(['B',3,1],3,1)1903sage: b = K.module_generators[0]1904sage: b.e(0)1905[--+, []]1906"""1907b = self.parent().to_ambient_crystal()(self).e_string([0,0])1908if b is None:1909return None1910return self.parent().from_ambient_crystal()(b)19111912def f0(self):1913r"""1914Gives `f_0` on self by mapping self to the ambient crystal, calculating `f_0` there and1915pulling the element back.19161917EXAMPLES::19181919sage: K=KirillovReshetikhinCrystal(['B',3,1],3,1)1920sage: b = K.module_generators[0]1921sage: b.f(0)19221923"""1924b = self.parent().to_ambient_crystal()(self).f_string([0,0])1925if b is None:1926return None1927return self.parent().from_ambient_crystal()(b)19281929def epsilon0(self):1930r"""1931Calculates `\epsilon_0` of self by mapping the element to the ambient crystal1932and calculating `\epsilon_0` there.19331934EXAMPLES::19351936sage: K=KirillovReshetikhinCrystal(['B',3,1],3,1)1937sage: b = K.module_generators[0]1938sage: b.epsilon(0)193911940"""1941b = self.parent().to_ambient_crystal()(self)1942return b.epsilon(0)/219431944def phi0(self):1945r"""1946Calculates `\phi_0` of self by mapping the element to the ambient crystal1947and calculating `\phi_0` there.19481949EXAMPLES::19501951sage: K=KirillovReshetikhinCrystal(['B',3,1],3,1)1952sage: b = K.module_generators[0]1953sage: b.phi(0)195401955"""1956b = self.parent().to_ambient_crystal()(self)1957return b.phi(0)/219581959KR_type_Bn.Element = KR_type_BnElement196019611962class KR_type_Cn(KirillovReshetikhinGenericCrystal, AffineCrystalFromClassical):1963r"""1964Class of Kirillov-Reshetikhin crystals `B^{n,s}` of type `C_n^{(1)}`.19651966EXAMPLES::19671968sage: K = KirillovReshetikhinCrystal(['C',3,1],3,1)1969sage: [[b,b.f(0)] for b in K]1970[[[[1], [2], [3]], None], [[[1], [2], [-3]], None], [[[1], [3], [-3]], None],1971[[[2], [3], [-3]], None], [[[1], [3], [-2]], None], [[[2], [3], [-2]], None],1972[[[2], [3], [-1]], [[1], [2], [3]]], [[[1], [-3], [-2]], None], [[[2], [-3], [-2]], None],1973[[[2], [-3], [-1]], [[1], [2], [-3]]], [[[3], [-3], [-2]], None], [[[3], [-3], [-1]],1974[[1], [3], [-3]]], [[[3], [-2], [-1]], [[1], [3], [-2]]], [[[-3], [-2], [-1]], [[1], [-3], [-2]]]]1975"""19761977def __init__(self, cartan_type, r, s):1978r"""1979Initializes a Kirillov-Reshetikhin crystal ``self``.19801981TESTS::19821983sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_Cn(['C',3,1], 3, 1)1984sage: K1985Kirillov-Reshetikhin crystal of type ['C', 3, 1] with (r,s)=(3,1)1986sage: TestSuite(K).run()1987"""1988KirillovReshetikhinGenericCrystal.__init__(self, cartan_type, r ,s)1989AffineCrystalFromClassical.__init__(self, cartan_type, self.classical_decomposition())19901991def classical_decomposition(self):1992r"""1993Specifies the classical crystal underlying the Kirillov-Reshetikhin crystal `B^{n,s}`1994of type `C_n^{(1)}`. It is given by `B^{n,s} \cong B(s \Lambda_n)`.19951996EXAMPLES::19971998sage: K = KirillovReshetikhinCrystal(['C',3,1],3,2)1999sage: K.classical_decomposition()2000The crystal of tableaux of type ['C', 3] and shape(s) [[2, 2, 2]]2001"""2002return CrystalOfTableaux(self.cartan_type().classical(), shape = [self.s()]*self.r() )20032004def from_highest_weight_vector_to_pm_diagram(self, b):2005"""2006This gives the bijection between an element b in the classical decomposition2007of the KR crystal that is `{2,3,..,n}`-highest weight and `\pm` diagrams.20082009EXAMPLES::20102011sage: K = KirillovReshetikhinCrystal(['C',3,1],3,2)2012sage: T = K.classical_decomposition()2013sage: b = T(rows=[[2, 2], [3, 3], [-3, -1]])2014sage: pm = K.from_highest_weight_vector_to_pm_diagram(b); pm2015[[0, 0], [1, 0], [0, 1], [0]]2016sage: pm.__repr__(pretty_printing=True)2017. .2018. +2019- -20202021sage: hw = [ b for b in T if all(b.epsilon(i)==0 for i in [2,3]) ]2022sage: all(K.from_pm_diagram_to_highest_weight_vector(K.from_highest_weight_vector_to_pm_diagram(b)) == b for b in hw)2023True2024"""2025n = self.cartan_type().rank()-12026inner = Partition([Integer(b.weight()[i]) for i in range(1,n+1)])2027inter = Partition([len([i for i in r if i>0]) for r in b.to_tableau()])2028outer = b.to_tableau().shape()2029return PMDiagram([self.r(), self.s(), outer, inter, inner], from_shapes=True)20302031def from_pm_diagram_to_highest_weight_vector(self, pm):2032"""2033This gives the bijection between a `\pm` diagram and an element b in the classical2034decomposition of the KR crystal that is {2,3,..,n}-highest weight.20352036EXAMPLES::20372038sage: K = KirillovReshetikhinCrystal(['C',3,1],3,2)2039sage: pm = sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[0, 0], [1, 0], [0, 1], [0]])2040sage: K.from_pm_diagram_to_highest_weight_vector(pm)2041[[2, 2], [3, 3], [-3, -1]]2042"""2043u = [b for b in self.classical_decomposition().module_generators if b.to_tableau().shape() == pm.outer_shape()][0]2044ct = self.cartan_type()2045rank = ct.rank()-12046ct_type = ct.classical().type()2047assert ct_type in ['C']2048list = []2049for h in pm.heights_of_addable_plus():2050list += range(1,h+1)2051for h in pm.heights_of_minus():2052list += range(1,rank+1)+[rank-1-k for k in range(rank-h)]2053for i in reversed(list):2054u = u.f(i)2055return u20562057class KR_type_CnElement(AffineCrystalFromClassicalElement):2058r"""2059Class for the elements in the Kirillov-Reshetikhin crystals `B^{n,s}` of type `C_n^{(1)}`.20602061EXAMPLES::20622063sage: K=KirillovReshetikhinCrystal(['C',3,1],3,2)2064sage: type(K.module_generators[0])2065<class 'sage.combinat.crystals.kirillov_reshetikhin.KR_type_Cn_with_category.element_class'>2066"""20672068def e0(self):2069r"""2070Gives `e_0` on self by going to the `\pm`-diagram corresponding to the `{2,...,n}`-highest weight2071vector in the component of `self`, then applying [Definition 6.1, 4], and pulling back from2072`\pm`-diagrams.20732074EXAMPLES::20752076sage: K=KirillovReshetikhinCrystal(['C',3,1],3,2)2077sage: b = K.module_generators[0]2078sage: b.e(0)2079[[1, 2], [2, 3], [3, -1]]2080sage: b = K(rows=[[1,2],[2,3],[3,-1]])2081sage: b.e(0)2082[[2, 2], [3, 3], [-1, -1]]2083sage: b=K(rows=[[1, -3], [3, -2], [-3, -1]])2084sage: b.e(0)2085[[3, -3], [-3, -2], [-1, -1]]2086"""2087n = self.parent().cartan_type().n2088[b,l] = self.lift().to_highest_weight(index_set=range(2,n+1))2089pm = self.parent().from_highest_weight_vector_to_pm_diagram(b)2090[l1,l2] = pm.pm_diagram[n-1]2091if l1 == 0:2092return None2093pm.pm_diagram[n-1] = [l1-1,l2+1]2094pm = PMDiagram(pm.pm_diagram)2095b = self.parent().from_pm_diagram_to_highest_weight_vector(pm)2096b = b.f_string(reversed(l))2097return self.parent().retract(b)20982099def f0(self):2100r"""2101Gives `e_0` on self by going to the `\pm`-diagram corresponding to the `{2,...,n}`-highest weight2102vector in the component of `self`, then applying [Definition 6.1, 4], and pulling back from2103`\pm`-diagrams.21042105EXAMPLES::21062107sage: K=KirillovReshetikhinCrystal(['C',3,1],3,1)2108sage: b = K.module_generators[0]2109sage: b.f(0)2110"""2111n = self.parent().cartan_type().n2112[b,l] = self.lift().to_highest_weight(index_set=range(2,n+1))2113pm = self.parent().from_highest_weight_vector_to_pm_diagram(b)2114[l1,l2] = pm.pm_diagram[n-1]2115if l2 == 0:2116return None2117pm.pm_diagram[n-1] = [l1+1,l2-1]2118pm = PMDiagram(pm.pm_diagram)2119b = self.parent().from_pm_diagram_to_highest_weight_vector(pm)2120b = b.f_string(reversed(l))2121return self.parent().retract(b)21222123def epsilon0(self):2124r"""2125Calculates `\epsilon_0` of self using Lemma 6.1 of [4].21262127EXAMPLES::21282129sage: K=KirillovReshetikhinCrystal(['C',3,1],3,1)2130sage: b = K.module_generators[0]2131sage: b.epsilon(0)213212133"""2134n = self.parent().cartan_type().n2135b = self.lift().to_highest_weight(index_set=range(2,n+1))[0]2136pm = self.parent().from_highest_weight_vector_to_pm_diagram(b)2137[l1,l2] = pm.pm_diagram[n-1]2138return l121392140def phi0(self):2141r"""2142Calculates `\phi_0` of self.21432144EXAMPLES::21452146sage: K=KirillovReshetikhinCrystal(['C',3,1],3,1)2147sage: b = K.module_generators[0]2148sage: b.phi(0)214902150"""2151n = self.parent().cartan_type().n2152b = self.lift().to_highest_weight(index_set=range(2,n+1))[0]2153pm = self.parent().from_highest_weight_vector_to_pm_diagram(b)2154[l1,l2] = pm.pm_diagram[n-1]2155return l221562157KR_type_Cn.Element = KR_type_CnElement215821592160class KR_type_Dn_twisted(KirillovReshetikhinGenericCrystal, AffineCrystalFromClassical):2161r"""2162Class of Kirillov-Reshetikhin crystals `B^{n,s}` of type `D_{n+1}^{(2)}`.21632164EXAMPLES::21652166sage: K = KirillovReshetikhinCrystal(['D',4,2],3,1)2167sage: [[b,b.f(0)] for b in K]2168[[[+++, []], None], [[++-, []], None], [[+-+, []], None], [[-++, []],2169[+++, []]], [[+--, []], None], [[-+-, []], [++-, []]], [[--+, []], [+-+, []]],2170[[---, []], [+--, []]]]2171"""21722173def __init__(self, cartan_type, r, s):2174r"""2175Initializes a Kirillov-Reshetikhin crystal ``self``.21762177TESTS::21782179sage: K = sage.combinat.crystals.kirillov_reshetikhin.KR_type_Dn_twisted(['D',4,2], 3, 1)2180sage: K2181Kirillov-Reshetikhin crystal of type ['C', 3, 1]^* with (r,s)=(3,1)2182sage: TestSuite(K).run()2183"""2184KirillovReshetikhinGenericCrystal.__init__(self, cartan_type, r ,s)2185AffineCrystalFromClassical.__init__(self, cartan_type, self.classical_decomposition())21862187def classical_decomposition(self):2188r"""2189Specifies the classical crystal underlying the Kirillov-Reshetikhin crystal `B^{n,s}`2190of type `D_{n+1}^{(2)}`. It is given by `B^{n,s} \cong B(s \Lambda_n)`.21912192EXAMPLES::21932194sage: K = KirillovReshetikhinCrystal(['D',4,2],3,1)2195sage: K.classical_decomposition()2196The crystal of tableaux of type ['B', 3] and shape(s) [[1/2, 1/2, 1/2]]2197sage: K = KirillovReshetikhinCrystal(['D',4,2],3,2)2198sage: K.classical_decomposition()2199The crystal of tableaux of type ['B', 3] and shape(s) [[1, 1, 1]]2200"""2201s = self.s()2202if is_even(s):2203s = int(s/2)2204else:2205s = s/22206return CrystalOfTableaux(self.cartan_type().classical(), shape = [s]*self.r() )22072208def from_highest_weight_vector_to_pm_diagram(self, b):2209"""2210This gives the bijection between an element b in the classical decomposition2211of the KR crystal that is `{2,3,..,n}`-highest weight and `\pm` diagrams.22122213EXAMPLES::22142215sage: K = KirillovReshetikhinCrystal(['D',4,2],3,1)2216sage: T = K.classical_decomposition()2217sage: hw = [ b for b in T if all(b.epsilon(i)==0 for i in [2,3]) ]2218sage: [K.from_highest_weight_vector_to_pm_diagram(b) for b in hw]2219[[[0, 0], [0, 0], [1, 0], [0]], [[0, 0], [0, 0], [0, 1], [0]]]22202221sage: K = KirillovReshetikhinCrystal(['D',4,2],3,2)2222sage: T = K.classical_decomposition()2223sage: hw = [ b for b in T if all(b.epsilon(i)==0 for i in [2,3]) ]2224sage: [K.from_highest_weight_vector_to_pm_diagram(b) for b in hw]2225[[[0, 0], [0, 0], [2, 0], [0]], [[0, 0], [0, 0], [0, 0], [2]], [[0, 0], [2, 0], [0, 0], [0]],2226[[0, 0], [0, 0], [0, 2], [0]]]22272228Note that, since the classical decomposition of this crystal is of type `B_n`, there can2229be (at most one) entry `0` in the `{2,3,...,n}`-highest weight elements at height `n`.2230In the following implementation this is realized as an empty column of height `n` since2231this uniquely specifies the existence of the `0`:22322233EXAMPLES::22342235sage: b = hw[1]2236sage: pm = K.from_highest_weight_vector_to_pm_diagram(b)2237sage: pm.__repr__(pretty_printing=True)2238. .2239. .2240. .22412242TESTS::22432244sage: all(K.from_pm_diagram_to_highest_weight_vector(K.from_highest_weight_vector_to_pm_diagram(b)) == b for b in hw)2245True2246sage: K = KirillovReshetikhinCrystal(['D',4,2],3,2)2247sage: T = K.classical_decomposition()2248sage: hw = [ b for b in T if all(b.epsilon(i)==0 for i in [2,3]) ]2249sage: all(K.from_pm_diagram_to_highest_weight_vector(K.from_highest_weight_vector_to_pm_diagram(b)) == b for b in hw)2250True2251sage: K = KirillovReshetikhinCrystal(['D',4,2],3,3)2252sage: T = K.classical_decomposition()2253sage: hw = [ b for b in T if all(b.epsilon(i)==0 for i in [2,3]) ]2254sage: all(K.from_pm_diagram_to_highest_weight_vector(K.from_highest_weight_vector_to_pm_diagram(b)) == b for b in hw)2255True22562257"""2258n = self.cartan_type().rank()-12259s = self.s()2260if is_odd(s):2261t = b[0]2262b = b[1]2263else:2264t = b.parent()(rows=[])2265inner = [Integer(2*b.weight()[i]+2*t.weight()[i]) for i in range(1,n+1)]2266inter1 = Partition([len([i for i in r if i>0]) for r in b.to_tableau()])2267inter = Partition([len([i for i in r if i>=0]) for r in b.to_tableau()])2268if inter != inter1:2269inner[n-1] += 22270inner = Partition(inner)2271inter = [2*i for i in inter]+[0]*(n-len(inter))2272w = t.weight()2273if w[0]==0 and w[n-1]==0:2274v = [0]*n2275else:2276v = [1]*n2277if w[0]<0 and w[n-1]>0:2278v[n-1]=02279elif w[0]>0 and w[n-1]<0:2280v[n-1]=02281v[n-2]=-12282inter = Partition([inter[i] + v[i] for i in range(n)])2283outer = Partition([s]*n)2284return PMDiagram([n, s, outer, inter, inner], from_shapes=True)22852286def from_pm_diagram_to_highest_weight_vector(self, pm):2287"""2288This gives the bijection between a `\pm` diagram and an element b in the classical2289decomposition of the KR crystal that is {2,3,..,n}-highest weight.22902291EXAMPLES::22922293sage: K = KirillovReshetikhinCrystal(['D',4,2],3,2)2294sage: pm = sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[0, 0], [0, 0], [0, 0], [2]])2295sage: K.from_pm_diagram_to_highest_weight_vector(pm)2296[[2], [3], [0]]2297"""2298u = self.classical_decomposition().module_generators[0]2299ct = self.cartan_type()2300rank = ct.rank()-12301assert ct.classical().type() in ['B']2302list = []2303plus = pm.heights_of_addable_plus()2304minus = pm.heights_of_minus()2305l = len([i for i in plus if i==rank-1])2306a = (len(plus) + l)/22307list += sum(([i]*a for i in range(1,rank+1)),[])2308a = (len(minus)-l)/22309list += (range(1,rank+1)+[rank])*a2310for i in reversed(list):2311u = u.f(i)2312return u23132314class KR_type_Dn_twistedElement(AffineCrystalFromClassicalElement):2315r"""2316Class for the elements in the Kirillov-Reshetikhin crystals `B^{n,s}` of type `D_{n+1}^{(2)}`.23172318EXAMPLES::23192320sage: K=KirillovReshetikhinCrystal(['D',4,2],3,2)2321sage: type(K.module_generators[0])2322<class 'sage.combinat.crystals.kirillov_reshetikhin.KR_type_Dn_twisted_with_category.element_class'>2323"""23242325def e0(self):2326r"""2327Gives `e_0` on self by going to the `\pm`-diagram corresponding to the `{2,...,n}`-highest weight2328vector in the component of `self`, then applying [Definition 6.2, 4], and pulling back from2329`\pm`-diagrams.23302331EXAMPLES::23322333sage: K=KirillovReshetikhinCrystal(['D',4,2],3,3)2334sage: b = K.module_generators[0]2335sage: b.e(0)2336[+++, [[2], [3], [0]]]2337"""2338n = self.parent().cartan_type().rank()-12339s = self.parent().s()2340[b,l] = self.lift().to_highest_weight(index_set=range(2,n+1))2341pm = self.parent().from_highest_weight_vector_to_pm_diagram(b)2342[l1,l2] = pm.pm_diagram[n-1]2343l3 = pm.pm_diagram[n-2][0]2344if l1+l2+l3==s and l1==0:2345return None2346if l1+l2+l3<s:2347pm.pm_diagram[n-1][1] = l2+22348pm.pm_diagram[n][0] -= 22349elif l1>1:2350pm.pm_diagram[n-1][0] = l1-22351pm.pm_diagram[n][0] += 22352elif l1 ==1:2353pm.pm_diagram[n-1][0] = 02354pm.pm_diagram[n-1][1] = l2+12355pm = PMDiagram(pm.pm_diagram)2356b = self.parent().from_pm_diagram_to_highest_weight_vector(pm)2357b = b.f_string(reversed(l))2358return self.parent().retract(b)23592360def f0(self):2361r"""2362Gives `e_0` on self by going to the `\pm`-diagram corresponding to the `{2,...,n}`-highest weight2363vector in the component of `self`, then applying [Definition 6.2, 4], and pulling back from2364`\pm`-diagrams.23652366EXAMPLES::23672368sage: K=KirillovReshetikhinCrystal(['D',4,2],3,2)2369sage: b = K.module_generators[0]2370sage: b.f(0)2371"""2372n = self.parent().cartan_type().rank()-12373s = self.parent().s()2374[b,l] = self.lift().to_highest_weight(index_set=range(2,n+1))2375pm = self.parent().from_highest_weight_vector_to_pm_diagram(b)2376[l1,l2] = pm.pm_diagram[n-1]2377l3 = pm.pm_diagram[n-2][0]2378if l1+l2+l3==s and l2==0:2379return None2380if l1+l2+l3<s:2381pm.pm_diagram[n-1][0] = l1+22382pm.pm_diagram[n][0] -= 22383elif l2>1:2384pm.pm_diagram[n-1][1] = l2-22385pm.pm_diagram[n][0] += 22386elif l2 ==1:2387pm.pm_diagram[n-1][1] = 02388pm.pm_diagram[n-1][0] = l1+12389pm = PMDiagram(pm.pm_diagram)2390b = self.parent().from_pm_diagram_to_highest_weight_vector(pm)2391b = b.f_string(reversed(l))2392return self.parent().retract(b)23932394def epsilon0(self):2395r"""2396Calculates `\epsilon_0` of self using Lemma 6.2 of [4].23972398EXAMPLES::23992400sage: K=KirillovReshetikhinCrystal(['D',4,2],3,1)2401sage: b = K.module_generators[0]2402sage: b.epsilon(0)240312404"""2405n = self.parent().cartan_type().rank()-12406s = self.parent().s()2407[b,l] = self.lift().to_highest_weight(index_set=range(2,n+1))2408pm = self.parent().from_highest_weight_vector_to_pm_diagram(b)2409l1 = pm.pm_diagram[n-1][0]2410l4 = pm.pm_diagram[n][0]2411return l1+l424122413def phi0(self):2414r"""2415Calculates `\phi_0` of self.24162417EXAMPLES::24182419sage: K=KirillovReshetikhinCrystal(['D',4,2],3,1)2420sage: b = K.module_generators[0]2421sage: b.phi(0)242202423"""2424n = self.parent().cartan_type().rank()-12425s = self.parent().s()2426[b,l] = self.lift().to_highest_weight(index_set=range(2,n+1))2427pm = self.parent().from_highest_weight_vector_to_pm_diagram(b)2428l2 = pm.pm_diagram[n-1][1]2429l4 = pm.pm_diagram[n][0]2430return l2+l424312432KR_type_Dn_twisted.Element = KR_type_Dn_twistedElement24332434#####################################################################24352436class PMDiagram(CombinatorialObject):2437"""2438Class of `\pm` diagrams. These diagrams are in one-to-one bijection with `X_{n-1}` highest weight vectors2439in an `X_n` highest weight crystal `X=B,C,D`. See Section 4.1 of A. Schilling, "Combinatorial structure of2440Kirillov-Reshetikhin crystals of type `D_n(1)`, `B_n(1)`, `A_{2n-1}(2)`", J. Algebra 319 (2008) 2938-29622441(arXiv:0704.2046[math.QA]).24422443The input is a list `pm = [[a_0,b_0],[a_1,b_1],...,[a_{n-1},b_{n-1}],[b_n]]` of 2-tuples and a last 1-tuple.2444The tuple `[a_i,b_i]` specifies the number of `a_i` + and `b_i` - in the i-th row of the pm diagram2445if `n-i` is odd and the number of `a_i` +- pairs above row `i` and `b_i` columns of height `i` not containing2446any + or - if `n-i` is even.24472448Setting the option 'from_shapes = True' one can also input a `\pm` diagram in terms of its2449outer, intermediate and inner shape by specifying a tuple [n, s, outer, intermediate, inner]2450where `s` is the width of the `\pm` diagram, and 'outer' , 'intermediate',2451and 'inner' are the outer, intermediate and inner shape, respectively.24522453EXAMPLES::24542455sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[0,1],[1,2],[1]])2456sage: pm.pm_diagram2457[[0, 1], [1, 2], [1]]2458sage: pm._list2459[1, 1, 2, 0, 1]2460sage: pm.n246122462sage: pm.width246352464sage: pm.__repr__(pretty_printing=True)2465. . . .2466. + - -2467sage: sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([2,5,[4,4],[4,2],[4,1]], from_shapes=True)2468[[0, 1], [1, 2], [1]]24692470TESTS::24712472sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[1,2],[1,1],[1,1],[1,1],[1]])2473sage: sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([pm.n, pm.width, pm.outer_shape(), pm.intermediate_shape(), pm.inner_shape()], from_shapes=True) == pm2474True2475sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[1,2],[1,2],[1,1],[1,1],[1,1],[1]])2476sage: sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([pm.n, pm.width, pm.outer_shape(), pm.intermediate_shape(), pm.inner_shape()], from_shapes=True) == pm2477True2478"""24792480def __init__(self, pm_diagram, from_shapes = None):2481r"""2482Initializes `\pm` diagrams.24832484TESTS::24852486sage: sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[0,1],[1,2],[1]])2487[[0, 1], [1, 2], [1]]2488sage: sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([2,5,[4,4],[4,2],[4,1]], from_shapes=True)2489[[0, 1], [1, 2], [1]]2490"""2491if from_shapes:2492n = pm_diagram[0]2493s = pm_diagram[1]2494outer = [s]+list(pm_diagram[2])+[0 for i in range(n)]2495intermediate = [s]+list(pm_diagram[3])+[0 for i in range(n)]2496inner = [s]+list(pm_diagram[4])+[0 for i in range(n)]2497pm = [[inner[n]]]2498for i in range(int((n+1)/2)):2499pm.append([intermediate[n-2*i]-inner[n-2*i], inner[n-2*i-1]-intermediate[n-2*i]])2500pm.append([outer[n-2*i]-inner[n-2*i-1], inner[n-2*i-2]-outer[n-2*i]])2501if is_odd(n):2502pm.pop(n+1)2503pm_diagram = list(reversed(pm))2504self.pm_diagram = pm_diagram2505self.n = len(pm_diagram)-12506self._list = [i for a in reversed(pm_diagram) for i in a]2507self.width = sum(i for i in self._list)25082509def __repr__(self, pretty_printing = None):2510"""2511Turning on pretty printing allows to display the pm diagram as a2512tableau with the + and - displayed25132514EXAMPLES::25152516sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[1,0],[0,1],[2,0],[0,0],[0]])2517sage: pm.__repr__(pretty_printing=True)2518. . . +2519. . - -2520+ +2521- -2522sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[0,2], [0,0], [0]])2523sage: pm.__repr__(pretty_printing=True)25242525"""2526if pretty_printing is None:2527return repr(self.pm_diagram)2528t = []2529ish = self.inner_shape() + [0]*self.n2530msh = self.intermediate_shape() + [0]*self.n2531osh = self.outer_shape() + [0]*self.n2532for i in range(self.n):2533t.append(['.']*ish[i]+['+']*(msh[i]-ish[i])+['-']*(osh[i]-msh[i]))2534t=[i for i in t if i!= []]2535return Tableau(t).pp()25362537def inner_shape(self):2538"""2539Returns the inner shape of the pm diagram25402541EXAMPLES::2542sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[0,1],[1,2],[1]])2543sage: pm.inner_shape()2544[4, 1]2545sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[1,2],[1,1],[1,1],[1,1],[1]])2546sage: pm.inner_shape()2547[7, 5, 3, 1]2548sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[1,2],[1,2],[1,1],[1,1],[1,1],[1]])2549sage: pm.inner_shape()2550[10, 7, 5, 3, 1]2551"""2552t = []2553ll = self._list2554for i in range(self.n):2555t.append(sum(ll[0:2*i+1]))2556return Partition(list(reversed(t)))25572558def outer_shape(self):2559"""2560Returns the outer shape of the pm diagram25612562EXAMPLES::25632564sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[0,1],[1,2],[1]])2565sage: pm.outer_shape()2566[4, 4]2567sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[1,2],[1,1],[1,1],[1,1],[1]])2568sage: pm.outer_shape()2569[8, 8, 4, 4]2570sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[1,2],[1,2],[1,1],[1,1],[1,1],[1]])2571sage: pm.outer_shape()2572[13, 8, 8, 4, 4]2573"""2574t = []2575ll = self._list2576for i in range((self.n)/2):2577t.append(sum(ll[0:4*i+4]))2578t.append(sum(ll[0:4*i+4]))2579if is_even(self.n+1):2580t.append(sum(ll[0:2*self.n+2]))2581return Partition(list(reversed(t)))25822583def intermediate_shape(self):2584"""2585Returns the intermediate shape of the pm diagram (inner shape plus positions of plusses)25862587EXAMPLES::25882589sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[0,1],[1,2],[1]])2590sage: pm.intermediate_shape()2591[4, 2]2592sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[1,2],[1,1],[1,1],[1,1],[1]])2593sage: pm.intermediate_shape()2594[8, 6, 4, 2]2595sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[1,2],[1,2],[1,1],[1,1],[1,1],[1]])2596sage: pm.intermediate_shape()2597[11, 8, 6, 4, 2]2598sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[1,0],[0,1],[2,0],[0,0],[0]])2599sage: pm.intermediate_shape()2600[4, 2, 2]2601sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[1, 0], [0, 0], [0, 0], [0, 0], [0]])2602sage: pm.intermediate_shape()2603[1]2604"""2605p = self.inner_shape()2606p = p + [0 for i in range(self.n)]2607ll = list(reversed(self._list))2608p = [ p[i]+ll[2*i+1] for i in range(self.n) ]2609return Partition(p)26102611def heights_of_minus(self):2612"""2613Returns a list with the heights of all minus in the `\pm` diagram.26142615EXAMPLES::26162617sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[1,2],[1,2],[1,1],[1,1],[1,1],[1]])2618sage: pm.heights_of_minus()2619[5, 5, 3, 3, 1, 1]2620sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[1,2],[1,1],[1,1],[1,1],[1]])2621sage: pm.heights_of_minus()2622[4, 4, 2, 2]2623"""2624n = self.n2625heights = []2626for i in range(int((n+1)/2)):2627heights += [n-2*i]*((self.outer_shape()+[0]*n)[n-2*i-1]-(self.intermediate_shape()+[0]*n)[n-2*i-1])2628return heights26292630def heights_of_addable_plus(self):2631"""2632Returns a list with the heights of all addable plus in the `\pm` diagram.26332634EXAMPLES::26352636sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[1,2],[1,2],[1,1],[1,1],[1,1],[1]])2637sage: pm.heights_of_addable_plus()2638[1, 1, 2, 3, 4, 5]2639sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[1,2],[1,1],[1,1],[1,1],[1]])2640sage: pm.heights_of_addable_plus()2641[1, 2, 3, 4]2642"""2643heights = []2644for i in range(1,self.n+1):2645heights += [i]*self.sigma().pm_diagram[i][0]2646return heights26472648def sigma(self):2649"""2650Returns sigma on pm diagrams as needed for the analogue of the Dynkin diagram automorphism2651that interchanges nodes `0` and `1` for type `D_n(1)`, `B_n(1)`, `A_{2n-1}(2)` for2652Kirillov-Reshetikhin crystals.26532654EXAMPLES::26552656sage: pm=sage.combinat.crystals.kirillov_reshetikhin.PMDiagram([[0,1],[1,2],[1]])2657sage: pm.sigma().pm_diagram2658[[1, 0], [2, 1], [1]]2659"""2660pm = self.pm_diagram2661return PMDiagram([list(reversed(a)) for a in pm])266226632664def partitions_in_box(r, s):2665"""2666Returns all partitions in a box of width s and height r.26672668EXAMPLES::26692670sage: sage.combinat.crystals.kirillov_reshetikhin.partitions_in_box(3,2)2671[[], [1], [2], [1, 1], [2, 1], [1, 1, 1], [2, 2], [2, 1, 1],2672[2, 2, 1], [2, 2, 2]]2673"""2674return [x for n in range(r*s+1) for x in Partitions(n,max_part=s,max_length=r)]26752676def vertical_dominoes_removed(r, s):2677"""2678Returns all partitions obtained from a rectangle of width s and height r by removing2679vertical dominoes.26802681EXAMPLES::26822683sage: sage.combinat.crystals.kirillov_reshetikhin.vertical_dominoes_removed(2,2)2684[[], [1, 1], [2, 2]]2685sage: sage.combinat.crystals.kirillov_reshetikhin.vertical_dominoes_removed(3,2)2686[[2], [2, 1, 1], [2, 2, 2]]2687sage: sage.combinat.crystals.kirillov_reshetikhin.vertical_dominoes_removed(4,2)2688[[], [1, 1], [1, 1, 1, 1], [2, 2], [2, 2, 1, 1], [2, 2, 2, 2]]2689"""2690return [x.conjugate() for x in horizontal_dominoes_removed(s,r)]26912692def horizontal_dominoes_removed(r, s):2693"""2694Returns all partitions obtained from a rectangle of width s and height r by removing2695horizontal dominoes.26962697EXAMPLES::26982699sage: sage.combinat.crystals.kirillov_reshetikhin.horizontal_dominoes_removed(2,2)2700[[], [2], [2, 2]]2701sage: sage.combinat.crystals.kirillov_reshetikhin.horizontal_dominoes_removed(3,2)2702[[], [2], [2, 2], [2, 2, 2]]2703"""2704list = [ [y for y in x] + [0 for i in range(r-x.length())] for x in partitions_in_box(r, int(s/2)) ]2705two = lambda x : 2*(x-int(s/2)) + s2706return [Partition([two(y) for y in x]) for x in list]270727082709