diff --git a/permutation.cc b/permutation.cc index 9d3545e..79bb4dd 100644 --- a/permutation.cc +++ b/permutation.cc @@ -817,7 +817,7 @@ template Partition::Partition(const YoungTableaux &x) { #ifdef DEBUG -if(x.is_valid()) laerror("operation with an invalid tableaux"); +if(!x.is_valid()) laerror("operation with an invalid tableaux"); #endif int nparts=x.size(); int n=0; @@ -1095,6 +1095,7 @@ if(!is_valid()) laerror("invalid young frame"); if(!is_standard()) laerror("nonstandardly filled young frame"); #endif + if(!ncyc) ncyc=max(); //number of types of applied points NRVec_from1 onxlines(0,ncyc); @@ -1116,6 +1117,10 @@ for(int i=1;i<=ncyc;i++) contrib += ((onxlines[i]&1)^1); return (1-2*(contrib&1)); //add it to the character +1 for even no. of odd apl., -1 for odd no. of odd apl. } +static bool _callyoung; + +template +static void (*_young_callback)(const YoungTableaux&); template static T _character; @@ -1243,7 +1248,15 @@ template void nextapply(T ncyc) { _nowapplying++; -if(ncyc> _ncycles) _character += _tchi->character_contribution(_ncycles); +if(ncyc> _ncycles) + { + if(_callyoung) + { + _young_callback(*_tchi); + _character ++; + } + else _character += _tchi->character_contribution(_ncycles); + } else regulapply(ncyc,(*_aplnumbers)[ncyc]); _nowapplying--; } @@ -1279,22 +1292,175 @@ if(aplnumbers[k]==1) //prepare static variables for the recursive procedure and generate all regular applications YoungTableaux y(irrep); //y.clear(); //already done in the constructor +_callyoung=false; _ncycles =ncycles; _tchi = &y; _nn = n; _nowapplying =0; _aplnumbers = &aplnumbers; _character =0; -_oclin = new Partition(n); -_occol = new Partition(n); +Partition oclin(n); +_oclin = &oclin; +Partition occol(n); +_occol = &occol; for(int i=1; i<=n; ++i) (*_oclin)[i]= (*_occol)[i]= 1; nextapply(1); -delete _occol; -delete _oclin; return _character; } + + +template +PERM_RANK_TYPE YoungTableaux::generate_all_standard(void (*callback)(const YoungTableaux&)) +{ +#ifdef DEBUG +if(!this->is_valid()) laerror("invalid young frame"); +#endif + +//prepare numbers to apply to the tableaux +T n=this->sum(); +T ncycles=n; +NRVec_from1 aplnumbers(n); +for(T i=1; i<=n; ++i) aplnumbers[i]=1; + +//prepare static variables for the recursive procedure and generate all regular applications +this->clear(); +_callyoung=true; +_young_callback =callback; +_ncycles =ncycles; +_tchi = this; +_nn = n; +_nowapplying =0; +_aplnumbers = &aplnumbers; +_character =0; +Partition oclin(n); +_oclin = &oclin; +Partition occol(n); +_occol = &occol; +for(int i=1; i<=n; ++i) (*_oclin)[i]= (*_occol)[i]= 1; +nextapply(1); +return _character; +} + + +////generation of the young operator +template +void (*_young_operator_callback)(const NRPerm&p, const T parity, const PERM_RANK_TYPE nterms); + +template +static NRPerm _aperm; + +template +static NRPerm _sperm; + +template +static const YoungTableaux *_tyou; + +template +static const Partition *_tyou_cols; + +template +static const Partition *_tyou_rows; + +static PERM_RANK_TYPE _nyoungterms, _expectterms; + +template +static T _antparity; + + + +template +void symetr(T ilin, T iel) +{ + +if(ilin > (*_tyou_cols)[1]) + { + ++_nyoungterms; + (*_young_operator_callback)(_aperm*_sperm,_antparity,_expectterms); + } +else if(iel > (*_tyou_rows)[ilin]) symetr(ilin+1,1); +else + { + int i; + + for(i=1;i<=(*_tyou_rows)[ilin];i++) + if(!_sperm[(*_tyou)[ilin][i]]) + { + _sperm[(*_tyou)[ilin][i]]= (*_tyou)[ilin][iel]; + symetr(ilin,iel+1); + _sperm[(*_tyou)[ilin][i]]=0; + } + } +} + + + + +template +void antisym(T icol,T iel) +{ + +if(icol > (*_tyou_rows)[1]) + { + _antparity = _aperm.parity(); + symetr(1,1); + } +else +if(iel > (*_tyou_cols)[icol]) antisym(icol+1,1); +else + { + int i; + + for(i=1;i<=(*_tyou_cols)[icol];i++) + if(!_aperm[(*_tyou)[i][icol]]) + { + _aperm[(*_tyou)[i][icol]]= (*_tyou)[iel][icol]; + antisym(icol,iel+1); + _aperm[(*_tyou)[i][icol]]=0; + } + } +} + + + + + + + + +template +PERM_RANK_TYPE YoungTableaux::young_operator(void (*callback)(const NRPerm&p, const T parity, const PERM_RANK_TYPE nterms)) const +{ +#ifdef DEBUG +if(!this->is_standard()) laerror("young_operator called for non-standard tableaux"); +#endif +_young_operator_callback = callback; +_nyoungterms =0; +_tyou = this; +Partition rows=Partition(*this); +Partition cols=rows.adjoint(); +_tyou_rows = &rows; +_tyou_cols = &cols; + +T n=rows.sum(); +_aperm.resize(n); _aperm.clear(); +_sperm.resize(n); _sperm.clear(); + + +_expectterms=1; +for(int i=1;i<=cols[1];i++) _expectterms *= factorial(rows[i]); +for(int i=1;i<=rows[1];i++) _expectterms *= factorial(cols[i]); + +antisym(1,1); + +if(_nyoungterms!=_expectterms) laerror("youngconstruct: inconsistent number of terms"); + +return _nyoungterms; +} + + + template static NRVec_from1 > *_irreps; diff --git a/permutation.h b/permutation.h index f7075d1..3ab787d 100644 --- a/permutation.h +++ b/permutation.h @@ -162,6 +162,15 @@ public: }; +template +extern T Sn_character(const Partition &irrep, const Partition &cclass); + +template +inline T Sn_character(const CompressedPartition &irrep, const CompressedPartition &cclass) +{ +return Sn_character(Partition(irrep),Partition(cclass)); +} + template class YoungTableaux : public NRVec_from1 > { @@ -177,8 +186,9 @@ public: T max() const; //get back highest number filled in NRVec_from1 yamanouchi() const; //yamanouchi symbol T character_contribution(int ncyc=0) const; //contribution of filled tableaux to Sn character + PERM_RANK_TYPE generate_all_standard(void (*callback)(const YoungTableaux&)); + PERM_RANK_TYPE young_operator(void (*callback)(const NRPerm&p, const T parity, const PERM_RANK_TYPE nterms)) const; //generate young operator for a standard tableaux - //@@@ ??>young operator as a linear comb of permutations - maybe a class for itself, i.e. element of the Sn group algebra? or maybe as a vector with index being the rank of the permutation(n! length) or as a sparsemat thereof or maybe a list??? }; template @@ -187,15 +197,6 @@ std::ostream & operator<<(std::ostream &s, const YoungTableaux &x); extern PERM_RANK_TYPE partitions(int n, int k= -1); //enumerate partitions to k parts; k== -1 for total # of partitions -template -extern T Sn_character(const Partition &irrep, const Partition &cclass); - -template -inline T Sn_character(const CompressedPartition &irrep, const CompressedPartition &cclass) -{ -return Sn_character(Partition(irrep),Partition(cclass)); -} - //Sn character table template diff --git a/t.cc b/t.cc index 6422657..3325c82 100644 --- a/t.cc +++ b/t.cc @@ -71,13 +71,30 @@ for(int i=0; i<4; ++i) static int unitary_n; static PERM_RANK_TYPE space_dim; +void yyprintme(const NRPerm&p, const int parity, const PERM_RANK_TYPE nterms) +{ +cout<< parity<<"/"<&y) +{ +cout < &p) { -CompressedPartition pc(p); -cout<<'['< pc(p); +cout<<'['< y(p); +PERM_RANK_TYPE dim=y.generate_all_standard(yprintme); + Partition q=p.adjoint(); PERM_RANK_TYPE snd=p.Sn_irrep_dim(); cout<<"IR dim "<>n >>unitary_n; @@ -2141,7 +2158,7 @@ if(tot!=partitions(n)) laerror("internal error in partition generation or enumer if(space_dim!=longpow(unitary_n,n)) {cout<>n ;