Cadabra
Computer algebra system for field theory problems
YoungTab.hh
Go to the documentation of this file.
1 /*
2 
3 Cadabra: a field-theory motivated computer algebra system.
4 Copyright (C) 2001-2011 Kasper Peeters <kasper.peeters@aei.mpg.de>
5 
6  This program is free software: you can redistribute it and/or
7 modify it under the terms of the GNU General Public License as
8 published by the Free Software Foundation, either version 3 of the
9 License, or (at your option) any later version.
10 
11  This program is distributed in the hope that it will be useful,
12  but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 General Public License for more details.
15 
16  You should have received a copy of the GNU General Public License
17  along with this program. If not, see <http://www.gnu.org/licenses/>.
18 
19 */
20 
21 /*
22 - TODO: has_nullifying trace is wrong, but needs to be merged with the
23  input_asym code in order to be more useful.
24 
25 */
26 
27 #pragma once
28 
29 #include <cstddef>
30 #include <iostream>
31 #include <iterator>
32 #include <vector>
33 #include <list>
34 #include <gmpxx.h>
35 #include "Combinatorics.hh"
36 #include <cstddef>
37 
38 typedef mpz_class yngint_t;
39 typedef mpq_class yngrat_t;
40 
42 namespace yngtab {
43 
44  // The tableau_base is the abstract interface; does not depend on the
45  // actual storage format.
46 
47  class tableau_base {
48  public:
49  tableau_base();
50  virtual ~tableau_base();
51  virtual unsigned int number_of_rows() const=0;
52  virtual unsigned int row_size(unsigned int row) const=0;
53  virtual unsigned int column_size(unsigned int col) const; // FIXME: maybe make pure virt too
54  virtual void add_box(unsigned int row)=0;
55  virtual void remove_box(unsigned int row)=0;
56  virtual void add_row(unsigned int row_size);
57  virtual void clear()=0;
58 
59  yngrat_t multiplicity; // also keeps track of signs
60  int selfdual_column; // -n, 0, n for antiselfdual, no, selfdual (count from 1)
61  yngint_t dimension(unsigned int) const;
62  unsigned long hook_length(unsigned int row, unsigned int col) const;
63  yngint_t hook_length_prod() const;
64  };
65 
66  class tableau : public tableau_base {
67  public:
68  tableau();
69  tableau(const tableau&);
70 
71  virtual ~tableau();
72  virtual unsigned int number_of_rows() const;
73  virtual unsigned int row_size(unsigned int row) const;
74  virtual void add_box(unsigned int row);
75  virtual void remove_box(unsigned int row);
76  virtual void clear();
77 
78  tableau& operator=(const tableau&);
79  private:
80  std::vector<int> rows;
81  };
82 
83  template<class T>
84  class tableaux;
85 
86  template<class T>
87  class filled_tableau : public tableau {
88  public:
89  typedef T value_type;
90 
93 
94  virtual ~filled_tableau();
95  virtual unsigned int number_of_rows() const;
96  virtual unsigned int row_size(unsigned int row) const;
97  virtual void add_box(unsigned int row);
98  virtual void remove_box(unsigned int row);
99  std::pair<int, int> find(const T&) const;
100  virtual void clear();
101 
102  void copy_shape(const tableau&);
103 
104  T& operator()(unsigned int row, unsigned int col);
105  const T& operator()(unsigned int row, unsigned int col) const;
106  const T& operator[](unsigned int boxnum) const;
107  void add_box(unsigned int rownum, T val);
108  void swap_columns(unsigned int c1, unsigned int c2);
109 
111  bool has_nullifying_trace() const;
113  void sort_columns();
115  void canonicalise();
116  std::pair<int, int> nonstandard_loc() const;
117  template<class StrictWeakOrdering> void sort_within_columns(StrictWeakOrdering comp);
118  template<class StrictWeakOrdering> void sort_columns(StrictWeakOrdering comp);
119  template<class StrictWeakOrdering> void canonicalise(StrictWeakOrdering comp, bool only_col_ex=false);
120  void projector(combin::symmetriser<T>&, bool modulo_monoterm=false) const;
123 
125 
127  public:
128  typedef T value_type;
129  typedef T* pointer;
130  typedef T& reference;
131  typedef size_t size_type;
132  typedef ptrdiff_t difference_type;
133  typedef std::random_access_iterator_tag iterator_category;
134  };
135 
137  public:
138  typedef T value_type;
139  typedef const T* pointer;
140  typedef const T& reference;
141  typedef size_t size_type;
142  typedef ptrdiff_t difference_type;
143  typedef std::random_access_iterator_tag iterator_category;
144  };
145 
146  class const_iterator;
147  class in_column_iterator;
149  class in_row_iterator;
150  class in_row_const_iterator;
151 
154  public:
155  in_column_iterator(unsigned int r, unsigned int c, filled_tableau<T> *);
156  T& operator*() const;
157  T* operator->() const;
162  in_column_iterator operator+(unsigned int) const;
163  in_column_iterator operator-(unsigned int) const;
166  T& operator[](int n) const;
167  bool operator<(const in_column_iterator& other) const;
168  bool operator>(const in_column_iterator& other) const;
169  bool operator<=(const in_column_iterator& other) const;
170  bool operator>=(const in_column_iterator& other) const;
171  ptrdiff_t operator-(const in_column_iterator&) const;
172  bool operator==(const in_column_iterator&) const;
173  bool operator!=(const in_column_iterator&) const;
174 
175  friend class filled_tableau<T>;
177  private:
179  unsigned int column_number, row_number;
180  };
181 
184  public:
185  in_column_const_iterator(unsigned int r, unsigned int c, const filled_tableau<T>*);
187  const T& operator*() const;
188  const T* operator->() const;
189  in_column_const_iterator& operator++();
190  in_column_const_iterator operator++(int);
191  in_column_const_iterator& operator--();
192  in_column_const_iterator operator--(int);
193  in_column_const_iterator operator+(unsigned int) const;
194  in_column_const_iterator operator-(unsigned int) const;
195  in_column_const_iterator& operator+=(unsigned int);
196  in_column_const_iterator& operator-=(unsigned int);
197  bool operator<(const in_column_const_iterator& other) const;
198  bool operator>(const in_column_const_iterator& other) const;
199  bool operator<=(const in_column_const_iterator& other) const;
200  bool operator>=(const in_column_const_iterator& other) const;
201  ptrdiff_t operator-(const in_column_const_iterator&) const;
202  bool operator==(const in_column_const_iterator&) const;
204 
205  friend class filled_tableau<T>;
206  private:
208  unsigned int column_number, row_number;
209  };
210 
213  public:
214  in_row_iterator(unsigned int r, unsigned int c, filled_tableau<T>*);
215  T& operator*() const;
216  T* operator->() const;
217  in_row_iterator& operator++();
218  in_row_iterator operator++(int);
219  in_row_iterator& operator--();
220  in_row_iterator operator--(int);
221  in_row_iterator operator+(unsigned int) const;
222  in_row_iterator operator-(unsigned int) const;
223  in_row_iterator& operator+=(unsigned int);
224  in_row_iterator& operator-=(unsigned int);
225  bool operator<(const in_row_iterator& other) const;
226  bool operator>(const in_row_iterator& other) const;
227  bool operator<=(const in_row_iterator& other) const;
228  bool operator>=(const in_row_iterator& other) const;
229  ptrdiff_t operator-(const in_row_iterator&) const;
230  bool operator==(const in_row_iterator&) const;
231  bool operator!=(const in_row_iterator&) const;
232 
233  friend class filled_tableau<T>;
235  private:
237  unsigned int column_number, row_number;
238  };
239 
241  public:
242  in_row_const_iterator(unsigned int r, unsigned int c, const filled_tableau<T>*);
244  const T& operator*() const;
245  const T* operator->() const;
246  in_row_const_iterator& operator++();
247  in_row_const_iterator operator++(int);
248  in_row_const_iterator& operator--();
249  in_row_const_iterator operator--(int);
250  in_row_const_iterator operator+(unsigned int) const;
251  in_row_const_iterator operator-(unsigned int) const;
252  in_row_const_iterator& operator+=(unsigned int);
253  in_row_const_iterator& operator-=(unsigned int);
254  bool operator<(const in_row_const_iterator& other) const;
255  bool operator>(const in_row_const_iterator& other) const;
256  bool operator<=(const in_row_const_iterator& other) const;
257  bool operator>=(const in_row_const_iterator& other) const;
258  ptrdiff_t operator-(const in_row_const_iterator&) const;
259  bool operator==(const in_row_const_iterator&) const;
260  bool operator!=(const in_row_const_iterator&) const;
261 
262  friend class filled_tableau<T>;
263  private:
265  unsigned int column_number, row_number;
266  };
267 
269  class iterator : public iterator_base {
270  public:
271  iterator(unsigned int r, unsigned int c, filled_tableau<T> *);
272  T& operator*() const;
273  T* operator->() const;
274  iterator& operator++();
275  iterator operator++(int);
276  iterator& operator--();
277  iterator operator--(int);
278  iterator operator+(unsigned int) const;
279  iterator operator-(unsigned int) const;
280  iterator& operator+=(unsigned int);
281  iterator& operator-=(unsigned int);
282  bool operator<(const iterator& other) const;
283  bool operator>(const iterator& other) const;
284  ptrdiff_t operator-(const iterator&) const;
285  bool operator==(const iterator&) const;
286  bool operator!=(const iterator&) const;
287 
288  friend class filled_tableau<T>;
289  friend class filled_tableau<T>::const_iterator;
290  private:
292  unsigned int column_number, row_number;
293  };
294 
296  public:
297  const_iterator(unsigned int r, unsigned int c, const filled_tableau<T>*);
298  const_iterator(const iterator& other);
299  const T& operator*() const;
300  const T* operator->() const;
301  const_iterator& operator++();
302  const_iterator operator++(int);
303  const_iterator& operator--();
304  const_iterator operator--(int);
305  const_iterator operator+(unsigned int) const;
306  const_iterator operator-(unsigned int) const;
307  const_iterator& operator+=(unsigned int);
308  const_iterator& operator-=(unsigned int);
309  bool operator<(const const_iterator& other) const;
310  bool operator>(const const_iterator& other) const;
311  ptrdiff_t operator-(const const_iterator&) const;
312  bool operator==(const const_iterator&) const;
313  bool operator!=(const const_iterator&) const;
314 
315  friend class filled_tableau<T>;
316  private:
318  unsigned int column_number, row_number;
319  };
320 
321 
324  in_column_const_iterator begin_column(unsigned int column_number) const;
325  in_column_const_iterator end_column(unsigned int column_number) const;
326  in_column_const_iterator cbegin_column(unsigned int column_number) const;
327  in_column_const_iterator cend_column(unsigned int column_number) const;
328  in_row_iterator begin_row(unsigned int row_number);
329  in_row_iterator end_row(unsigned int row_number);
330  in_row_const_iterator begin_row(unsigned int row_number) const;
331  in_row_const_iterator end_row(unsigned int row_number) const;
332  in_row_const_iterator cbegin_row(unsigned int row_number) const;
333  in_row_const_iterator cend_row(unsigned int row_number) const;
334  iterator begin();
335  iterator end();
336  const_iterator begin() const;
337  const_iterator end() const;
338  const_iterator cbegin() const;
339  const_iterator cend() const;
340 
341  template<class OutputIterator>
342  OutputIterator Garnir_set(OutputIterator, unsigned int, unsigned int) const;
343  private:
344  typedef std::vector<T> box_row;
345  typedef std::vector<box_row> row_stack;
347  };
348 
349  template<class T>
350  class tableaux {
351  public:
352  yngint_t total_dimension(unsigned int dim);
353  void remove_nullifying_traces();
356  bool standard_form();
357  void add_tableau(const T&);
358  void symmetrise(const T& tabsym);
359 
360  typedef std::list<T> tableau_container_t;
362 
363  typedef std::back_insert_iterator<tableau_container_t> back_insert_iterator;
364 
365  back_insert_iterator get_back_insert_iterator();
366  };
367 
368  bool legal_box(const std::vector<std::pair<int,int> >& prev,
369  const std::vector<std::pair<int,int> >& ths,
370  int colpos, int trypos);
371 
372  // --------------------------------------
373 
374 
375  template<class T>
377  {
378  return back_insert_iterator(storage);
379  }
380 
381  template<class T>
383  {
384  typename tableau_container_t::iterator it=storage.begin();
385  while(it!=storage.end()) {
386  if(it->has_nullifying_trace())
387  it=storage.erase(it);
388  else ++it;
389  }
390  }
391 
392  template<class T>
393  void tableaux<T>::symmetrise(const T&)
394  {
395  //
396  // typename tableau_container_t::iterator thetab=storage.begin();
397  // while(thetab!=storage.end()) {
398  // (*thetab).sort_columns();
399  // std::pair<int,int> where=(*thetab).nonstandard_loc();
400  // if(where.first!=-1) {
401  // combinations<typename T::value_type> com;
402  //
403 
404  /*
405  FIXME: we should have two LR_tensor routines, because if you do 'alltabs', you should
406  keep track of which boxes came from tableau 2. So do a LR_tensor with numbered boxes,
407  and then after the LR_tensor apply the symmetries of the original tableaux, put back
408  the original index names, sort columns and determine whether the tableau is identically
409  non-zero. Then add to the product.
410 
411  Another issue: adding to tableaux should have an option to not insert doubles.
412 
413  There was something third, forgotten...
414  */
415  }
416 
417  template<class T>
419  {
420  rows.clear();
421  for(unsigned int r=0; r<other.number_of_rows(); ++r) {
422  rows.push_back(box_row(other.row_size(r)));
423  }
424  tableau::operator=(other);
425  }
426 
427  template<class T>
429  {
430  return (rows==other.rows);
431  }
432 
433  template<class T>
435  {
436  return false;
437 
438  // Old, probably incorrect code:
439  //
440  // for(unsigned int r1=0; r1<number_of_rows(); ++r1) {
441  // for(unsigned c1=0; c1<row_size(r1); ++c1) {
442  // for(unsigned int c2=c1+1; c2<row_size(r1); ++c2) {
443  // // (r1,c1) and (r1,c2)
444  // for(unsigned int c3=0; c3<row_size(0); ++c3) {
445  // unsigned int r3=0;
446  // while(r3<number_of_rows()-1 && c3<row_size(r3)) {
447  // unsigned int r4=r3+1;
448  // while(r4<number_of_rows() && c3<row_size(r4)) {
449  // if((rows[r1][c1]==rows[r3][c3] && rows[r1][c2]==rows[r4][c3]) ||
450  // (rows[r1][c1]==rows[r4][c3] && rows[r1][c2]==rows[r3][c3]) )
451  // return true;
452  // ++r4;
453  // }
454  // ++r3;
455  // }
456  // }
457  // }
458  // }
459  // }
460  // return false;
461  }
462 
463  template<class T>
464  std::pair<int, int> filled_tableau<T>::find(const T& obj) const
465  {
466  for(unsigned int ir=0; ir<rows.size(); ++ir) {
467  for(unsigned int ic=0; ic<rows[ir].size(); ++ic) {
468  if(rows[ir][ic]==obj)
469  return std::pair<int,int>(ir, ic);
470  }
471  }
472  return std::pair<int,int>(-1,-1);
473  }
474 
475  template<class T>
477  {
478  std::less<T> comp;
479  sort_within_columns(comp);
480  }
481 
482  template<class T>
484  {
485  std::less<T> comp;
486  sort_columns(comp);
487  }
488 
489  template<class T>
491  {
492  std::less<T> comp;
493  canonicalise(comp);
494  }
495 
496  template<class T>
497  template<class StrictWeakOrdering>
498  void filled_tableau<T>::sort_within_columns(StrictWeakOrdering comp)
499  {
500  filled_tableau<T> tmp(*this);
501  if(number_of_rows()==0) return;
502  for(unsigned int c=0; c<row_size(0); ++c) {
503  std::sort(begin_column(c), end_column(c), comp);
505  }
506  }
507 
508  template<class T>
509  template<class StrictWeakOrdering>
510  void filled_tableau<T>::sort_columns(StrictWeakOrdering comp)
511  {
512  for(unsigned int c1=0; c1<row_size(0); ++c1) {
513  for(unsigned int c2=c1; c2<row_size(0); ++c2) {
514  if(column_size(c1)==column_size(c2)) {
515  if(comp((*this)(0,c2), (*this)(0,c1)))
516  swap_columns(c1,c2);
517  }
518  }
519  }
520  }
521 
522  template<class T>
523  template<class StrictWeakOrdering>
524  void filled_tableau<T>::canonicalise(StrictWeakOrdering comp, bool only_col_ex)
525  {
526  if(!only_col_ex)
527  sort_within_columns(comp);
528  sort_columns(comp);
529  }
530 
531  //---------------------------------------------------------------------------
532  // in_column_iterator
533 
534  template<class T>
536  : tab(t), column_number(c), row_number(r)
537  {
538  }
539 
540  template<class T>
542  {
543  typename filled_tableau<T>::in_column_iterator it2(*this);
544  it2+=n;
545  return it2;
546  }
547 
548  template<class T>
550  {
551  typename filled_tableau<T>::in_column_iterator it2(*this);
552  it2-=n;
553  return it2;
554  }
555 
556  template<class T>
558  {
559  return row_number-other.row_number;
560  }
561 
562  template<class T>
564  {
565  return (*tab)(row_number + n, column_number);
566  }
567 
568  template<class T>
570  {
571  return (*tab)(row_number,column_number);
572  }
573 
574  template<class T>
576  {
577  return &((*tab)(row_number,column_number));
578  }
579 
580  template<class T>
582  {
583  ++row_number;
584  return (*this);
585  }
586 
587  template<class T>
589  {
590  row_number+=n;
591  return (*this);
592  }
593 
594  template<class T>
596  {
597  --row_number;
598  return (*this);
599  }
600 
601  template<class T>
603  {
604  in_column_iterator tmp(*this);
605  --row_number;
606  return tmp;
607  }
608 
609  template<class T>
611  {
612  in_column_iterator tmp(*this);
613  ++row_number;
614  return tmp;
615  }
616 
617  template<class T>
619  {
620  row_number-=n;
621  return (*this);
622  }
623 
624  template<class T>
626  {
627  if(tab==other.tab && row_number==other.row_number && column_number==other.column_number)
628  return true;
629  return false;
630  }
631 
632  template<class T>
634  {
635  if(row_number<=other.row_number) return true;
636  return false;
637  }
638 
639  template<class T>
641  {
642  if(row_number>=other.row_number) return true;
643  return false;
644  }
645 
646  template<class T>
648  {
649  if(row_number<other.row_number) return true;
650  return false;
651  }
652 
653  template<class T>
655  {
656  if(row_number>other.row_number) return true;
657  return false;
658  }
659 
660  template<class T>
662  {
663  return !((*this)==other);
664  }
665 
666  //---------------------------------------------------------------------------
667 // in_column_const_iterator
668 
669  template<class T>
671  : tab(t), column_number(c), row_number(r)
672  {
673  }
674 
675  template<class T>
677  : tab(other.tab), column_number(other.column_number), row_number(other.row_number)
678  {
679  }
680 
681  template<class T>
683  {
685  it2 += n;
686  return it2;
687  }
688 
689  template<class T>
691  {
693  it2 -= n;
694  return it2;
695  }
696 
697  template<class T>
699  {
700  return row_number - other.row_number;
701  }
702 
703  template<class T>
705  {
706  return (*tab)(row_number, column_number);
707  }
708 
709  template<class T>
711  {
712  return &((*tab)(row_number, column_number));
713  }
714 
715  template<class T>
717  {
718  ++row_number;
719  return (*this);
720  }
721 
722  template<class T>
724  {
725  row_number += n;
726  return (*this);
727  }
728 
729  template<class T>
731  {
732  --row_number;
733  return (*this);
734  }
735 
736  template<class T>
738  {
739  in_column_const_iterator tmp(*this);
740  --row_number;
741  return tmp;
742  }
743 
744  template<class T>
746  {
747  in_column_const_iterator tmp(*this);
748  ++row_number;
749  return tmp;
750  }
751 
752  template<class T>
754  {
755  row_number -= n;
756  return (*this);
757  }
758 
759  template<class T>
761  {
762  if (tab == other.tab && row_number == other.row_number && column_number == other.column_number)
763  return true;
764  return false;
765  }
766 
767  template<class T>
769  {
770  if (row_number <= other.row_number) return true;
771  return false;
772  }
773 
774  template<class T>
776  {
777  if (row_number >= other.row_number) return true;
778  return false;
779  }
780 
781  template<class T>
783  {
784  if (row_number < other.row_number) return true;
785  return false;
786  }
787 
788  template<class T>
790  {
791  if (row_number > other.row_number) return true;
792  return false;
793  }
794 
795  template<class T>
797  {
798  return !((*this) == other);
799  }
800 
801 
802  //---------------------------------------------------------------------------
803  // in_row_iterator
804 
805  template<class T>
807  : tab(t), column_number(c), row_number(r)
808  {
809  }
810 
811  template<class T>
813  {
814  typename filled_tableau<T>::in_row_iterator it2(*this);
815  it2 += n;
816  return it2;
817  }
818 
819  template<class T>
821  {
822  typename filled_tableau<T>::in_row_iterator it2(*this);
823  it2 -= n;
824  return it2;
825  }
826 
827  template<class T>
829  {
830  return column_number - other.column_number;
831  }
832 
833  template<class T>
835  {
836  return (*tab)(row_number, column_number);
837  }
838 
839  template<class T>
841  {
842  return &((*tab)(row_number, column_number));
843  }
844 
845  template<class T>
847  {
848  ++column_number;
849  return (*this);
850  }
851 
852  template<class T>
854  {
855  column_number += n;
856  return (*this);
857  }
858 
859  template<class T>
861  {
862  --column_number;
863  return (*this);
864  }
865 
866  template<class T>
868  {
869  in_row_iterator tmp(*this);
870  --column_number;
871  return tmp;
872  }
873 
874  template<class T>
876  {
877  in_row_iterator tmp(*this);
878  ++column_number;
879  return tmp;
880  }
881 
882  template<class T>
884  {
885  column_number -= n;
886  return (*this);
887  }
888 
889  template<class T>
891  {
892  if (tab == other.tab && row_number == other.row_number && column_number == other.column_number)
893  return true;
894  return false;
895  }
896 
897  template<class T>
899  {
900  if (column_number <= other.column_number) return true;
901  return false;
902  }
903 
904  template<class T>
906  {
907  if (column_number >= other.column_number) return true;
908  return false;
909  }
910 
911  template<class T>
913  {
914  if (column_number < other.column_number) return true;
915  return false;
916  }
917 
918  template<class T>
920  {
921  if (column_number > other.column_number) return true;
922  return false;
923  }
924 
925  template<class T>
927  {
928  return !((*this) == other);
929  }
930 
931  //---------------------------------------------------------------------------
932 // in_row_const_iterator
933 
934  template<class T>
936  : tab(t), column_number(c), row_number(r)
937  {
938  }
939 
940  template<class T>
942  : tab(other.tab), column_number(other.column_number), row_number(other.row_number)
943  {
944  }
945 
946 
947  template<class T>
949  {
950  typename filled_tableau<T>::in_row_const_iterator it2(*this);
951  it2 += n;
952  return it2;
953  }
954 
955  template<class T>
957  {
958  typename filled_tableau<T>::in_row_const_iterator it2(*this);
959  it2 -= n;
960  return it2;
961  }
962 
963  template<class T>
965  {
966  return column_number - other.column_number;
967  }
968 
969  template<class T>
971  {
972  return (*tab)(row_number, column_number);
973  }
974 
975  template<class T>
977  {
978  return &((*tab)(row_number, column_number));
979  }
980 
981  template<class T>
983  {
984  ++column_number;
985  return (*this);
986  }
987 
988  template<class T>
990  {
991  column_number += n;
992  return (*this);
993  }
994 
995  template<class T>
997  {
998  --column_number;
999  return (*this);
1000  }
1001 
1002  template<class T>
1004  {
1005  in_row_const_iterator tmp(*this);
1006  --column_number;
1007  return tmp;
1008  }
1009 
1010  template<class T>
1012  {
1013  in_row_const_iterator tmp(*this);
1014  ++column_number;
1015  return tmp;
1016  }
1017 
1018  template<class T>
1020  {
1021  column_number -= n;
1022  return (*this);
1023  }
1024 
1025  template<class T>
1027  {
1028  if (tab == other.tab && row_number == other.row_number && column_number == other.column_number)
1029  return true;
1030  return false;
1031  }
1032 
1033  template<class T>
1035  {
1036  if (column_number <= other.column_number) return true;
1037  return false;
1038  }
1039 
1040  template<class T>
1042  {
1043  if (column_number >= other.column_number) return true;
1044  return false;
1045  }
1046 
1047  template<class T>
1049  {
1050  if (column_number < other.column_number) return true;
1051  return false;
1052  }
1053 
1054  template<class T>
1056  {
1057  if (column_number > other.column_number) return true;
1058  return false;
1059  }
1060 
1061  template<class T>
1063  {
1064  return !((*this) == other);
1065  }
1066 
1067 
1068 
1069  //---------------------------------------------------------------------------
1070  // iterator
1071 
1072  template<class T>
1073  filled_tableau<T>::iterator::iterator(unsigned int r, unsigned int c, filled_tableau<T> *t)
1074  : tab(t), column_number(c), row_number(r)
1075  {
1076  }
1077 
1078  template<class T>
1080  {
1081  typename filled_tableau<T>::iterator it2(*this);
1082  it2+=n;
1083  return it2;
1084  }
1085 
1086  template<class T>
1088  {
1089  typename filled_tableau<T>::iterator it2(*this);
1090  it2-=n;
1091  return it2;
1092  }
1093 
1094  template<class T>
1095  ptrdiff_t filled_tableau<T>::iterator::operator-(const iterator& other) const
1096  {
1097  return row_number-other.row_number;
1098  }
1099 
1100  template<class T>
1102  {
1103  return (*tab)(row_number,column_number);
1104  }
1105 
1106  template<class T>
1108  {
1109  return &((*tab)(row_number,column_number));
1110  }
1111 
1112  template<class T>
1114  {
1115  if(++column_number==tab->rows[row_number].size()) {
1116  column_number=0;
1117  ++row_number;
1118  }
1119  return (*this);
1120  }
1121 
1122  template<class T>
1124  {
1125  while(n>0) {
1126  if(++column_number==tab->rows[row_number]) {
1127  column_number=0;
1128  ++row_number;
1129  }
1130  --n;
1131  }
1132  return (*this);
1133  }
1134 
1135  template<class T>
1137  {
1138  if(column_number==0) {
1139  --row_number;
1140  column_number=tab->rows[row_number].size()-1;
1141  }
1142  else --column_number;
1143  return (*this);
1144  }
1145 
1146  template<class T>
1148  {
1149  iterator tmp(*this);
1150  if(column_number==0) {
1151  --row_number;
1152  column_number=tab->rows[row_number].size()-1;
1153  }
1154  else --column_number;
1155  return tmp;
1156  }
1157 
1158  template<class T>
1160  {
1161  iterator tmp(*this);
1162  while(this->n>0) {
1163  if(++column_number==tab->rows[row_number]) {
1164  column_number=0;
1165  ++row_number;
1166  }
1167  --this->n;
1168  }
1169  return tmp;
1170  }
1171 
1172  template<class T>
1174  {
1175  while(n>0) {
1176  if(column_number==0) {
1177  --row_number;
1178  column_number=tab->rows[row_number].size()-1;
1179  }
1180  else --column_number;
1181  --n;
1182  }
1183  return (*this);
1184  }
1185 
1186  template<class T>
1188  {
1189  if(tab==other.tab && row_number==other.row_number && column_number==other.column_number)
1190  return true;
1191  return false;
1192  }
1193 
1194  template<class T>
1196  {
1197  if(row_number<other.row_number) return true;
1198  return false;
1199  }
1200 
1201  template<class T>
1203  {
1204  if(row_number>other.row_number) return true;
1205  return false;
1206  }
1207 
1208  template<class T>
1210  {
1211  return !((*this)==other);
1212  }
1213 
1214 
1215 
1216  //---------------------------------------------------------------------------
1217  // const_iterator
1218 
1219  template<class T>
1221  : tab(t), column_number(c), row_number(r)
1222  {
1223  }
1224 
1225  template<class T>
1227  : tab(other.tab), column_number(other.column_number), row_number(other.row_number)
1228  {
1229  }
1230 
1231  template<class T>
1233  {
1234  typename filled_tableau<T>::const_iterator it2(*this);
1235  it2 += n;
1236  return it2;
1237  }
1238 
1239  template<class T>
1241  {
1242  typename filled_tableau<T>::const_iterator it2(*this);
1243  it2 -= n;
1244  return it2;
1245  }
1246 
1247  template<class T>
1249  {
1250  return row_number - other.row_number;
1251  }
1252 
1253  template<class T>
1255  {
1256  return (*tab)(row_number, column_number);
1257  }
1258 
1259  template<class T>
1261  {
1262  return &((*tab)(row_number, column_number));
1263  }
1264 
1265  template<class T>
1267  {
1268  if (++column_number == tab->rows[row_number].size()) {
1269  column_number = 0;
1270  ++row_number;
1271  }
1272  return (*this);
1273  }
1274 
1275  template<class T>
1277  {
1278  while (n > 0) {
1279  if (++column_number == tab->rows[row_number]) {
1280  column_number = 0;
1281  ++row_number;
1282  }
1283  --n;
1284  }
1285  return (*this);
1286  }
1287 
1288  template<class T>
1290  {
1291  if (column_number == 0) {
1292  --row_number;
1293  column_number = tab->rows[row_number].size() - 1;
1294  }
1295  else --column_number;
1296  return (*this);
1297  }
1298 
1299  template<class T>
1301  {
1302  const_iterator tmp(*this);
1303  if (column_number == 0) {
1304  --row_number;
1305  column_number = tab->rows[row_number].size() - 1;
1306  }
1307  else --column_number;
1308  return tmp;
1309  }
1310 
1311  template<class T>
1313  {
1314  const_iterator tmp(*this);
1315  while (this->n > 0) {
1316  if (++column_number == tab->rows[row_number]) {
1317  column_number = 0;
1318  ++row_number;
1319  }
1320  --this->n;
1321  }
1322  return tmp;
1323  }
1324 
1325  template<class T>
1327  {
1328  while (n > 0) {
1329  if (column_number == 0) {
1330  --row_number;
1331  column_number = tab->rows[row_number].size() - 1;
1332  }
1333  else --column_number;
1334  --n;
1335  }
1336  return (*this);
1337  }
1338 
1339  template<class T>
1341  {
1342  if (tab == other.tab && row_number == other.row_number && column_number == other.column_number)
1343  return true;
1344  return false;
1345  }
1346 
1347  template<class T>
1349  {
1350  if (row_number < other.row_number) return true;
1351  return false;
1352  }
1353 
1354  template<class T>
1356  {
1357  if (row_number > other.row_number) return true;
1358  return false;
1359  }
1360 
1361  template<class T>
1363  {
1364  return !((*this) == other);
1365  }
1366 
1367 
1368  //---
1369  // other
1370 
1371  template<class T>
1373  {
1374  return iterator(0, 0, this);
1375  }
1376 
1377  template<class T>
1379  {
1380  return iterator(rows.size(), 0, this);
1381  }
1382 
1383 
1384  template<class T>
1386  {
1387  return const_iterator(0,0,this);
1388  }
1389 
1390  template<class T>
1392  {
1393  return const_iterator(rows.size(), 0, this);
1394  }
1395 
1396  template<class T>
1398  {
1399  return cbegin();
1400  }
1401 
1402  template<class T>
1404  {
1405  return cend();
1406  }
1407 
1408  template<class T>
1410  {
1411  typename filled_tableau<T>::in_column_iterator it(0,column,this);
1412  assert(number_of_rows()>0);
1413  assert(column<row_size(0));
1414  return it;
1415  }
1416 
1417  template<class T>
1419  {
1420  unsigned int r=0;
1421  while(r<number_of_rows()) {
1422  if(row_size(r)<=column)
1423  break;
1424  ++r;
1425  }
1426  typename filled_tableau<T>::in_column_iterator it(r,column,this);
1427  return it;
1428  }
1429 
1430  template<class T>
1432  {
1433  typename filled_tableau<T>::in_column_const_iterator it(0, column, this);
1434  assert(number_of_rows() > 0);
1435  assert(column < row_size(0));
1436  return it;
1437  }
1438 
1439  template<class T>
1441  {
1442  unsigned int r = 0;
1443  while (r < number_of_rows()) {
1444  if (row_size(r) <= column)
1445  break;
1446  ++r;
1447  }
1448  typename filled_tableau<T>::in_column_const_iterator it(r, column, this);
1449  return it;
1450  }
1451 
1452  template<class T>
1454  {
1455  return cbegin_column(column);
1456  }
1457 
1458  template<class T>
1460  {
1461  return cend_column(column);
1462  }
1463 
1464  template<class T>
1466  {
1467  return in_row_iterator{ row, 0, this };
1468  }
1469 
1470  template<class T>
1472  {
1473  return in_row_iterator{ row, row_size(row), this };
1474  }
1475 
1476  template<class T>
1478  {
1479  return in_row_const_iterator{ row, 0, this };
1480  }
1481 
1482  template<class T>
1484  {
1485  return in_row_const_iterator{ row, row_size(row), this };
1486  }
1487 
1488  template<class T>
1490  {
1491  return cbegin_row(row);
1492  }
1493 
1494  template<class T>
1496  {
1497  return cend_row(row);
1498  }
1499 
1500 
1501 
1502 
1503  template<class T>
1504  template<class OutputIterator>
1505  OutputIterator filled_tableau<T>::Garnir_set(OutputIterator it, unsigned int row, unsigned int col) const
1506  {
1507  assert(col>0);
1508  unsigned int r=row, c=col;
1509  *it=(*this)(r,c);
1510  ++it;
1511  while(r>0) {
1512  --r;
1513  *it=(*this)(r,c);
1514  ++it;
1515  }
1516  r=row;
1517  --c;
1518  *it=(*this)(r,c);
1519  ++it;
1520  while(r+1<column_size(c)) {
1521  ++r;
1522  *it=(*this)(r,c);
1523  ++it;
1524  }
1525  return it;
1526  }
1527 
1528  template<class T>
1529  std::pair<int, int> filled_tableau<T>::nonstandard_loc() const
1530  {
1531  unsigned int r=number_of_rows();
1532  assert(r>0);
1533  do {
1534  --r;
1535  for(unsigned int c=0; c<row_size(r)-1; ++c) {
1536  if((*this)(r,c) > (*this)(r,c+1) )
1537  return std::pair<int, int>(r,c);
1538  }
1539  }
1540  while(r>0);
1541  return std::pair<int,int>(-1,-1);
1542  }
1543 
1544  template<class T>
1546  {
1547  bool already_standard=true;
1548 
1549  typename tableau_container_t::iterator thetab=storage.begin();
1550  while(thetab!=storage.end()) {
1551  (*thetab).sort_within_columns();
1552  std::pair<int,int> where=(*thetab).nonstandard_loc();
1553  if(where.first!=-1) {
1554  already_standard=false;
1556  for(unsigned int i1=where.first; i1<(*thetab).column_size(where.second); ++i1)
1557  com.original.push_back((*thetab)(i1,where.second));
1558  for(unsigned int i1=0; i1<=(unsigned int)(where.first); ++i1)
1559  com.original.push_back((*thetab)(i1,where.second+1));
1560  com.sublengths.push_back((*thetab).column_size(where.second)-where.first);
1561  com.sublengths.push_back(where.first+1);
1562  com.permute();
1563  for(unsigned int tabi=1; tabi<com.size(); ++tabi) {
1564  T ntab((*thetab));
1565  unsigned int offset=0;
1566  for(unsigned int i1=where.first; i1<(*thetab).column_size(where.second); ++i1, ++offset)
1567  ntab(i1,where.second)=com[tabi][offset];
1568  for(unsigned int i1=0; i1<=(unsigned int)(where.first); ++i1, ++offset)
1569  ntab(i1,where.second+1)=com[tabi][offset];
1570  ntab.multiplicity*=-1*com.ordersign(tabi);
1571  add_tableau(ntab);
1572  }
1573  thetab=storage.erase(thetab);
1574  }
1575  else ++thetab;
1576  }
1577  return already_standard;
1578  }
1579 
1580  template<class T>
1581  void tableaux<T>::add_tableau(const T& ntab)
1582  {
1583  typename tableau_container_t::iterator it=storage.begin();
1584  while(it!=storage.end()) {
1585  if((*it).compare_without_multiplicity(ntab)) {
1586  (*it).multiplicity+=ntab.multiplicity;
1587  if((*it).multiplicity==0)
1588  storage.erase(it);
1589  return;
1590  }
1591  ++it;
1592  }
1593  storage.push_back(ntab);
1594  }
1595 
1596 
1597  template<class T>
1599  {
1600  yngrat_t norm=1;
1601  norm/=hook_length_prod();
1602  return norm;
1603  }
1604 
1605  template<class T>
1606  void filled_tableau<T>::projector(combin::symmetriser<T>& sym, bool modulo_monoterm) const
1607  {
1608  for(unsigned int r=0; r<number_of_rows(); ++r)
1609  for(unsigned int c=0; c<row_size(r); ++c)
1610  sym.original.push_back(rows[r][c]);
1611 
1612  unsigned int offset=0;
1613  // symmetrise over boxes in rows
1614  for(unsigned int r=0; r<number_of_rows(); ++r) {
1615  sym.permutation_sign=1;
1616  sym.permute_blocks.clear();
1617  sym.block_length=1;
1618  sym.input_asym.clear();
1619  for(unsigned int c=0; c<row_size(r); ++c)
1620  sym.permute_blocks.push_back(offset++);
1621  sym.apply_symmetry();
1622  }
1623  // sym.collect();
1624  // anti-symmetrise over boxes in columns
1625  if(modulo_monoterm) {
1626  int newmult=1;
1627  for(unsigned int c=0; c<row_size(0); ++c)
1628  newmult*=combin::factorial(column_size(c));
1629  for(unsigned int i=0; i<sym.size(); ++i)
1630  sym.set_multiplicity(i, sym.signature(i)*newmult);
1631  }
1632  else {
1633  sym.permute_blocks.clear();
1634  for(unsigned int c=0; c<row_size(0); ++c) {
1635  unsigned int r=0;
1636  sym.value_permute.clear();
1637  sym.permutation_sign=-1;
1638  sym.input_asym.clear();
1639  while(r<number_of_rows() && c<row_size(r))
1640  sym.value_permute.push_back(rows[r++][c]);
1641  if(sym.value_permute.size()>1)
1642  sym.apply_symmetry();
1643  }
1644  }
1645  // sym.collect();
1646  }
1647 
1648  template<class T>
1650  combin::range_vector_t& sublengths_scattered) const
1651  {
1652  for(unsigned int r=0; r<number_of_rows(); ++r)
1653  for(unsigned int c=0; c<row_size(r); ++c)
1654  sym.original.push_back(rows[r][c]);
1655 
1656  unsigned int offset=0;
1657  // symmetrise over boxes in rows
1658  for(unsigned int r=0; r<number_of_rows(); ++r) {
1659  sym.permutation_sign=1;
1660  sym.permute_blocks.clear();
1661  sym.block_length=1;
1662  sym.input_asym.clear();
1663  for(unsigned int c=0; c<row_size(r); ++c)
1664  sym.permute_blocks.push_back(offset++);
1665  sym.apply_symmetry();
1666  }
1668  sym.permute_blocks.clear();
1669  for(unsigned int c=0; c<row_size(0); ++c) {
1670  unsigned int r=0;
1671  sym.value_permute.clear();
1672  sym.permutation_sign=-1;
1673  while(r<number_of_rows() && c<row_size(r))
1674  sym.value_permute.push_back(rows[r++][c]);
1675 
1676  sym.sublengths_scattered=sublengths_scattered;
1677 
1678  // // Now setup sublengths_scattered to take into account
1679  // // asym_ranges. These asym_ranges refer to values stored in the
1680  // // boxes of the full tableau. We need to find the locations of
1681  // // these values inside the full original, as that is what goes
1682  // // into sublengths_scattered.
1683  //
1684  // sym.input_asym.clear();
1685  // sym.sublengths.clear();
1686  // sym.sublengths_scattered.clear();
1687  // for(unsigned int m=0; m<sym.value_permute.size(); ++m) {
1688  // // Try to find this value in an asym range.
1689  // unsigned int overlap=0;
1690  // for(unsigned int n=0; n<asym_ranges.size(); ++n) {
1691  // for(unsigned int nn=0; nn<asym_ranges[n].size(); ++nn) {
1692  // if(sym.value_permute[m]==asym_ranges[n][nn]) {
1693  // std::cout << "found " << sym.value_permute[m] << " in range" << std::endl;
1694  // // FIXME: this assumes that even though asym_ranges[n] is a superset
1695  // // of the current part of value_permute, elements are in the same order.
1696  // ++m; ++nn;
1697  // while(nn<asym_ranges[n].size()) {
1698  // if(sym.value_permute[m]==asym_ranges[n][nn]) {
1699  // std::cout << "same range: " << sym.value_permute[m] << std::endl;
1700  // ++m;
1701  // ++overlap;
1702  // }
1703  // ++nn;
1704  // }
1705  // break;
1706  // }
1707  // }
1708  // }
1709  // if(overlap>0) --m;
1710  // sym.sublengths.push_back(overlap+1);
1711  // }
1712  // unsigned int sum=0;
1713  // for(unsigned int m=0; m<sym.sublengths.size(); ++m)
1714  // sum+=sym.sublengths[m];
1715  //
1716  // std::cout << sum << " " << sym.value_permute.size() << std::endl;
1717  // assert(sum==sym.value_permute.size());
1718 
1719  // All set to run...
1720  if(sym.value_permute.size()>1)
1721  sym.apply_symmetry();
1722  }
1723  }
1724 
1725  template<class T>
1727  : tableau()
1728  {
1729  }
1730 
1731  template<class T>
1733  : tableau(other), rows(other.rows)
1734  {
1735  }
1736 
1737  template<class T>
1739  {
1740  rows=other.rows;
1741  tableau::operator=(other);
1742  return (*this);
1743  }
1744 
1745  template<class T>
1747  {
1748  yngint_t totdim=0;
1749  typename tableau_container_t::const_iterator it=storage.begin();
1750  while(it!=storage.end()) {
1751  totdim+=(*it).dimension(dim);
1752  ++it;
1753  }
1754  return totdim;
1755  }
1756 
1757  template<class T, class OutputIterator>
1758  void LR_tensor(const tableaux<T>& tabs1, const T& tab2, unsigned int maxrows,
1759  OutputIterator out, bool alltabs=false)
1760  {
1762  while(it!=tabs1.storage.end()) {
1763  LR_tensor((*it), tab2, maxrows, out, alltabs);
1764  ++it;
1765  }
1766  }
1767 
1768  template<class T1, class T2>
1769  void add_box(T1& tab1, unsigned int row1,
1770  const T2& tab2, unsigned int row2, unsigned int col2)
1771  {
1772  tab1.add_box(row1, tab2(row2,col2));
1773  }
1774 
1775  template<class T1>
1776  void add_box(T1& tab1, unsigned int row1,
1777  const tableau&, unsigned int, unsigned int)
1778  {
1779  tab1.add_box(row1);
1780  }
1781 
1783 
1784  template<class Tab, class OutputIterator>
1785  void LR_add_box(const Tab& tab2, Tab& newtab,
1786  unsigned int currow2, unsigned int curcol2, unsigned int startrow,
1787  unsigned int maxrows,
1788  OutputIterator outit,
1789  keeptrack_tab_t& Ycurrent,
1790  bool alltabs)
1791  {
1792  // Are we at the end of the current row of boxes in tab2 ?
1793  if((++curcol2)==tab2.row_size(currow2)) {
1794  // Are we at the end of tab2 altogether?
1795  if((++currow2)==tab2.number_of_rows()) {
1796  *outit=newtab; // Store the product tableau just created.
1797  return;
1798  }
1799  curcol2=0;
1800  startrow=0;
1801  }
1802 
1803  // Rule "row_by_row".
1804  for(unsigned int rowpos=startrow; rowpos<std::min(newtab.number_of_rows()+1,maxrows); ++rowpos) {
1805  // Rule "always_young".
1806  if(rowpos>0 && rowpos<newtab.number_of_rows())
1807  if(newtab.row_size(rowpos-1)==newtab.row_size(rowpos))
1808  continue; // No, would lead to non-Young tableau shape.
1809 
1810  // The column where the box will be added.
1811  unsigned int colpos=(rowpos==newtab.number_of_rows())?0:newtab.row_size(rowpos);
1812 
1813  // Rule "avoid_sym2asym".
1814  for(unsigned int rr=0; rr<rowpos; ++rr)
1815  if(Ycurrent(rr,colpos).first==(int)(currow2))
1816  goto rule_violated;
1817 
1818  // Rule "avoid_asym2sym".
1819  if(alltabs) // if not generating all tabs, ordered will take care of this already.
1820  for(unsigned int cc=0; cc<colpos; ++cc)
1821  if(Ycurrent(rowpos,cc).second==(int)(curcol2))
1822  goto rule_violated;
1823 
1824  // Rule "ordered".
1825  if(!alltabs && currow2>0) {
1826  int numi=0, numimin1=0;
1827  if(rowpos>0) {
1828  for(unsigned int sr=0; sr<rowpos; ++sr) // top to bottom
1829  for(unsigned int sc=0; sc<Ycurrent.row_size(sr); ++sc) { // right to left
1830  // Count all boxes from currow2 and from currow2-1.
1831  if(Ycurrent(sr,sc).first==(int)(currow2)) ++numi;
1832  if(Ycurrent(sr,sc).first==(int)(currow2)-1) ++numimin1;
1833  }
1834  }
1835  ++numi; // the box to be added
1836  if(numi>numimin1)
1837  goto rule_violated;
1838 
1839  // continue counting to see whether a previously valid box is now invalid
1840  for(unsigned int sr=rowpos; sr<Ycurrent.number_of_rows(); ++sr) // top to bottom
1841  for(int sc=Ycurrent.row_size(sr)-1; sc>=0; --sc) { // right to left
1842  if(Ycurrent(sr,sc).first==(int)(currow2)) ++numi;
1843  if(Ycurrent(sr,sc).first==(int)(currow2)-1) ++numimin1;
1844  if(numi>numimin1)
1845  goto rule_violated;
1846  }
1847  }
1848 
1849  // Put the box at row 'rowpos' and call LR_add_box recursively
1850  // to add the other boxes.
1851  Ycurrent.add_box(rowpos, std::pair<int,int>(currow2, curcol2));
1852  add_box(newtab, rowpos, tab2, currow2, curcol2);
1853  LR_add_box(tab2, newtab, currow2, curcol2, alltabs?0:rowpos, maxrows,
1854  outit, Ycurrent, alltabs);
1855 
1856  // Remove the box again in preparation for trying to add it to other rows.
1857  newtab.remove_box(rowpos);
1858  Ycurrent.remove_box(rowpos);
1859 
1860 rule_violated:
1861  ;
1862  }
1863  }
1864 
1865  template<class Tab, class OutputIterator>
1866  void LR_tensor(const Tab& tab1, const Tab& tab2, unsigned int maxrows,
1867  OutputIterator outit, bool alltabs=false)
1868  {
1869  // Make a copy of tab1 because LR_add_box has to change it and
1870  // tab1 is const here.
1871  Tab newtab(tab1);
1872 
1873  // Tableau which keeps track of the LR rules. It contains the
1874  // current (incomplete) shape of the tensor product, and for all boxes
1875  // which come from tab2 we store the row and column of tab2
1876  // from which they originated. Tab1 boxes have (-2,-2) stored.
1877  keeptrack_tab_t Ycurrent;
1878  Ycurrent.copy_shape(tab1);
1879  keeptrack_tab_t::iterator yi=Ycurrent.begin();
1880  while(yi!=Ycurrent.end()) {
1881  (*yi)=std::pair<int,int>(-2,-2);
1882  ++yi;
1883  }
1884 
1885  LR_add_box(tab2, newtab, 0, -1, 0, maxrows, outit, Ycurrent, alltabs);
1886  }
1887 
1888  template<class T, class OutputIterator>
1889  void LR_tensor(const tableaux<T>&, bool, unsigned int, OutputIterator )
1890  {
1891  assert(1==0);
1892  }
1893 
1894 
1895 
1896  std::ostream& operator<<(std::ostream&, const tableau& );
1897 
1898  template<class T>
1899  std::ostream& operator<<(std::ostream&, const tableaux<T>& );
1900 
1901  template<class T>
1902  std::ostream& operator<<(std::ostream&, const filled_tableau<T>& );
1903 
1904  template<class T>
1906  {
1907  return rows.size();
1908  }
1909 
1910  template<class T>
1911  unsigned int filled_tableau<T>::row_size(unsigned int num) const
1912  {
1913  assert(num<rows.size());
1914  return rows[num].size();
1915  }
1916 
1917  template<class T>
1918  T& filled_tableau<T>::operator()(unsigned int row, unsigned int col)
1919  {
1920  assert(row<rows.size());
1921  assert(col<rows[row].size());
1922  return rows[row][col];
1923  }
1924 
1925  template<class T>
1926  const T& filled_tableau<T>::operator()(unsigned int row, unsigned int col) const
1927  {
1928  assert(row<rows.size());
1929  assert(col<rows[row].size());
1930  return rows[row][col];
1931  }
1932 
1933  template<class T>
1934  const T& filled_tableau<T>::operator[](unsigned int boxnum) const
1935  {
1936  unsigned int row = 0;
1937  while (true) {
1938  if (boxnum < row_size(row))
1939  break;
1940  boxnum -= row_size(row);
1941  ++row;
1942  }
1943  return rows[row][boxnum];
1944  }
1945 
1946  template<class T>
1948  {
1949  }
1950 
1951  template<class T>
1952  void filled_tableau<T>::add_box(unsigned int rownum)
1953  {
1954  if(rownum>=rows.size())
1955  rows.resize(rownum+1);
1956  assert(rownum<rows.size());
1957  rows[rownum].push_back(T());
1958  }
1959 
1960  template<class T>
1961  void filled_tableau<T>::add_box(unsigned int rownum, T val)
1962  {
1963  if(rownum>=rows.size())
1964  rows.resize(rownum+1);
1965  assert(rownum<rows.size());
1966  rows[rownum].push_back(val);
1967  }
1968 
1969  template<class T>
1970  void filled_tableau<T>::swap_columns(unsigned int c1, unsigned int c2)
1971  {
1972  assert(c1<row_size(0) && c2<row_size(0));
1973  assert(column_size(c1)==column_size(c2));
1974  for(unsigned int r=0; r<column_size(c1); ++r) {
1975  T tmp=(*this)(r,c1);
1976  (*this)(r,c1)=(*this)(r,c2);
1977  (*this)(r,c2)=tmp;
1978  }
1979  }
1980 
1981  template<class T>
1982  void filled_tableau<T>::remove_box(unsigned int rownum)
1983  {
1984  assert(rownum<rows.size());
1985  assert(rows[rownum].size()>0);
1986  rows[rownum].pop_back();
1987  if(rows[rownum].size()==0)
1988  rows.pop_back();
1989  }
1990 
1991  template<class T>
1993  {
1994  rows.clear();
1995  tableau::clear();
1996  }
1997 
1998  template<class T>
1999  std::ostream& operator<<(std::ostream& str, const tableaux<T>& tabs)
2000  {
2002  while(it!=tabs.storage.end()) {
2003  str << (*it) << std::endl << std::endl;
2004  ++it;
2005  }
2006  return str;
2007  }
2008 
2009  template<class T>
2010  std::ostream& operator<<(std::ostream& str, const filled_tableau<T>& tab)
2011  {
2012  for(unsigned int i=0; i<tab.number_of_rows(); ++i) {
2013  for(unsigned int j=0; j<tab.row_size(i); ++j) {
2014  // str << "|" << tab(i,j) << "|";
2015  str << tab(i,j);
2016  }
2017  if(i==0) {
2018  str << " " << tab.dimension(10);
2019  if(tab.has_nullifying_trace()) str << " null";
2020  }
2021  if(i!=tab.number_of_rows()-1)
2022  str << std::endl;
2023  else
2024  str << " (" << tab.multiplicity << ")" << std::endl;
2025  }
2026  return str;
2027  }
2028 
2029  };
2030 
2031 
mpq_class yngrat_t
Definition: YoungTab.hh:39
mpz_class yngint_t
Definition: YoungTab.hh:38
std::vector< unsigned int > sublengths
Definition: Combinatorics.hh:74
std::vector< T > original
Definition: Combinatorics.hh:76
void permute(long start=-1, long end=-1)
Definition: Combinatorics.hh:351
Definition: Combinatorics.hh:101
int ordersign(unsigned int) const
Definition: Combinatorics.hh:458
unsigned int size() const
Definition: Combinatorics.hh:429
Definition: Combinatorics.hh:154
unsigned int size() const
Definition: Combinatorics.hh:906
void apply_symmetry(long start=-1, long end=-1)
Definition: Combinatorics.hh:695
int permutation_sign
Definition: Combinatorics.hh:163
range_vector_t sublengths_scattered
Definition: Combinatorics.hh:167
std::vector< unsigned int > permute_blocks
Definition: Combinatorics.hh:161
std::vector< T > original
Definition: Combinatorics.hh:159
range_vector_t input_asym
Definition: Combinatorics.hh:166
std::vector< T > value_permute
Definition: Combinatorics.hh:162
void set_multiplicity(unsigned int pos, int val)
Definition: Combinatorics.hh:1003
unsigned int block_length
Definition: Combinatorics.hh:160
int signature(unsigned int) const
Definition: Combinatorics.hh:996
size_t size_type
Definition: YoungTab.hh:141
T value_type
Definition: YoungTab.hh:138
const T * pointer
Definition: YoungTab.hh:139
const T & reference
Definition: YoungTab.hh:140
ptrdiff_t difference_type
Definition: YoungTab.hh:142
std::random_access_iterator_tag iterator_category
Definition: YoungTab.hh:143
Definition: YoungTab.hh:295
const T & operator*() const
Definition: YoungTab.hh:1254
bool operator==(const const_iterator &) const
Definition: YoungTab.hh:1340
bool operator<(const const_iterator &other) const
Definition: YoungTab.hh:1348
bool operator!=(const const_iterator &) const
Definition: YoungTab.hh:1362
const_iterator & operator++()
Definition: YoungTab.hh:1266
const_iterator(unsigned int r, unsigned int c, const filled_tableau< T > *)
Definition: YoungTab.hh:1220
const T * operator->() const
Definition: YoungTab.hh:1260
const_iterator(const iterator &other)
bool operator>(const const_iterator &other) const
Definition: YoungTab.hh:1355
const_iterator operator+(unsigned int) const
Definition: YoungTab.hh:1232
const_iterator & operator+=(unsigned int)
Definition: YoungTab.hh:1276
const_iterator operator-(unsigned int) const
Definition: YoungTab.hh:1240
unsigned int column_number
Definition: YoungTab.hh:318
unsigned int row_number
Definition: YoungTab.hh:318
const_iterator & operator-=(unsigned int)
Definition: YoungTab.hh:1326
const filled_tableau< T > * tab
Definition: YoungTab.hh:317
const_iterator & operator--()
Definition: YoungTab.hh:1289
A const iterator which stays inside a given column of a tableau.
Definition: YoungTab.hh:183
in_column_const_iterator & operator+=(unsigned int)
Definition: YoungTab.hh:723
bool operator<(const in_column_const_iterator &other) const
Definition: YoungTab.hh:782
const T * operator->() const
Definition: YoungTab.hh:710
in_column_const_iterator(unsigned int r, unsigned int c, const filled_tableau< T > *)
Definition: YoungTab.hh:670
in_column_const_iterator operator+(unsigned int) const
Definition: YoungTab.hh:682
in_column_const_iterator & operator--()
Definition: YoungTab.hh:730
in_column_const_iterator operator-(unsigned int) const
Definition: YoungTab.hh:690
unsigned int column_number
Definition: YoungTab.hh:208
bool operator<=(const in_column_const_iterator &other) const
Definition: YoungTab.hh:768
in_column_const_iterator & operator-=(unsigned int)
Definition: YoungTab.hh:753
bool operator>(const in_column_const_iterator &other) const
Definition: YoungTab.hh:789
bool operator!=(const in_column_const_iterator &) const
Definition: YoungTab.hh:796
unsigned int row_number
Definition: YoungTab.hh:208
const filled_tableau< T > * tab
Definition: YoungTab.hh:207
const T & operator*() const
Definition: YoungTab.hh:704
bool operator>=(const in_column_const_iterator &other) const
Definition: YoungTab.hh:775
in_column_const_iterator(const in_column_iterator &other)
bool operator==(const in_column_const_iterator &) const
Definition: YoungTab.hh:760
in_column_const_iterator & operator++()
Definition: YoungTab.hh:716
An iterator which stays inside a given column of a tableau.
Definition: YoungTab.hh:153
T * operator->() const
Definition: YoungTab.hh:575
in_column_iterator operator+(unsigned int) const
Definition: YoungTab.hh:541
filled_tableau< T > * tab
Definition: YoungTab.hh:178
in_column_iterator & operator--()
Definition: YoungTab.hh:595
bool operator>(const in_column_iterator &other) const
Definition: YoungTab.hh:654
bool operator>=(const in_column_iterator &other) const
Definition: YoungTab.hh:640
T & operator*() const
Definition: YoungTab.hh:569
unsigned int row_number
Definition: YoungTab.hh:179
bool operator==(const in_column_iterator &) const
Definition: YoungTab.hh:625
bool operator<(const in_column_iterator &other) const
Definition: YoungTab.hh:647
T & operator[](int n) const
Definition: YoungTab.hh:563
in_column_iterator operator-(unsigned int) const
Definition: YoungTab.hh:549
in_column_iterator & operator++()
Definition: YoungTab.hh:581
bool operator!=(const in_column_iterator &) const
Definition: YoungTab.hh:661
in_column_iterator & operator-=(unsigned int)
Definition: YoungTab.hh:618
in_column_iterator(unsigned int r, unsigned int c, filled_tableau< T > *)
Definition: YoungTab.hh:535
unsigned int column_number
Definition: YoungTab.hh:179
in_column_iterator & operator+=(unsigned int)
Definition: YoungTab.hh:588
bool operator<=(const in_column_iterator &other) const
Definition: YoungTab.hh:633
bool operator<(const in_row_const_iterator &other) const
Definition: YoungTab.hh:1048
bool operator<=(const in_row_const_iterator &other) const
Definition: YoungTab.hh:1034
in_row_const_iterator & operator+=(unsigned int)
Definition: YoungTab.hh:989
bool operator>=(const in_row_const_iterator &other) const
Definition: YoungTab.hh:1041
in_row_const_iterator(unsigned int r, unsigned int c, const filled_tableau< T > *)
Definition: YoungTab.hh:935
bool operator==(const in_row_const_iterator &) const
Definition: YoungTab.hh:1026
in_row_const_iterator & operator--()
Definition: YoungTab.hh:996
const T & operator*() const
Definition: YoungTab.hh:970
unsigned int column_number
Definition: YoungTab.hh:265
in_row_const_iterator operator+(unsigned int) const
Definition: YoungTab.hh:948
const T * operator->() const
Definition: YoungTab.hh:976
bool operator>(const in_row_const_iterator &other) const
Definition: YoungTab.hh:1055
in_row_const_iterator & operator++()
Definition: YoungTab.hh:982
in_row_const_iterator(const in_row_iterator &other)
bool operator!=(const in_row_const_iterator &) const
Definition: YoungTab.hh:1062
in_row_const_iterator & operator-=(unsigned int)
Definition: YoungTab.hh:1019
const filled_tableau< T > * tab
Definition: YoungTab.hh:264
unsigned int row_number
Definition: YoungTab.hh:265
in_row_const_iterator operator-(unsigned int) const
Definition: YoungTab.hh:956
An iterator which stays inside a given row of a tableau.
Definition: YoungTab.hh:212
in_row_iterator operator+(unsigned int) const
Definition: YoungTab.hh:812
bool operator==(const in_row_iterator &) const
Definition: YoungTab.hh:890
T * operator->() const
Definition: YoungTab.hh:840
T & operator*() const
Definition: YoungTab.hh:834
bool operator>(const in_row_iterator &other) const
Definition: YoungTab.hh:919
in_row_iterator(unsigned int r, unsigned int c, filled_tableau< T > *)
Definition: YoungTab.hh:806
bool operator<=(const in_row_iterator &other) const
Definition: YoungTab.hh:898
bool operator>=(const in_row_iterator &other) const
Definition: YoungTab.hh:905
bool operator<(const in_row_iterator &other) const
Definition: YoungTab.hh:912
in_row_iterator operator-(unsigned int) const
Definition: YoungTab.hh:820
unsigned int column_number
Definition: YoungTab.hh:237
in_row_iterator & operator+=(unsigned int)
Definition: YoungTab.hh:853
unsigned int row_number
Definition: YoungTab.hh:237
filled_tableau< T > * tab
Definition: YoungTab.hh:236
in_row_iterator & operator++()
Definition: YoungTab.hh:846
in_row_iterator & operator--()
Definition: YoungTab.hh:860
bool operator!=(const in_row_iterator &) const
Definition: YoungTab.hh:926
in_row_iterator & operator-=(unsigned int)
Definition: YoungTab.hh:883
Definition: YoungTab.hh:126
ptrdiff_t difference_type
Definition: YoungTab.hh:132
T & reference
Definition: YoungTab.hh:130
T * pointer
Definition: YoungTab.hh:129
size_t size_type
Definition: YoungTab.hh:131
std::random_access_iterator_tag iterator_category
Definition: YoungTab.hh:133
T value_type
Definition: YoungTab.hh:128
An iterator over all boxes of a tableau, left to right, top to bottom.
Definition: YoungTab.hh:269
iterator operator-(unsigned int) const
Definition: YoungTab.hh:1087
filled_tableau< T > * tab
Definition: YoungTab.hh:291
unsigned int column_number
Definition: YoungTab.hh:292
T * operator->() const
Definition: YoungTab.hh:1107
iterator & operator--()
Definition: YoungTab.hh:1136
bool operator>(const iterator &other) const
Definition: YoungTab.hh:1202
iterator operator+(unsigned int) const
Definition: YoungTab.hh:1079
iterator & operator+=(unsigned int)
Definition: YoungTab.hh:1123
bool operator<(const iterator &other) const
Definition: YoungTab.hh:1195
iterator & operator-=(unsigned int)
Definition: YoungTab.hh:1173
iterator(unsigned int r, unsigned int c, filled_tableau< T > *)
Definition: YoungTab.hh:1073
iterator & operator++()
Definition: YoungTab.hh:1113
unsigned int row_number
Definition: YoungTab.hh:292
T & operator*() const
Definition: YoungTab.hh:1101
bool operator==(const iterator &) const
Definition: YoungTab.hh:1187
bool operator!=(const iterator &) const
Definition: YoungTab.hh:1209
Definition: YoungTab.hh:87
const T & operator()(unsigned int row, unsigned int col) const
Definition: YoungTab.hh:1926
virtual ~filled_tableau()
Definition: YoungTab.hh:1947
void projector(combin::symmetriser< T > &, combin::range_vector_t &) const
Definition: YoungTab.hh:1649
void canonicalise(StrictWeakOrdering comp, bool only_col_ex=false)
Definition: YoungTab.hh:524
T value_type
Definition: YoungTab.hh:89
in_row_iterator end_row(unsigned int row_number)
Definition: YoungTab.hh:1471
std::vector< T > box_row
Definition: YoungTab.hh:344
const_iterator begin() const
Definition: YoungTab.hh:1397
void sort_columns()
Definition: YoungTab.hh:483
void add_box(unsigned int rownum, T val)
Definition: YoungTab.hh:1961
in_column_const_iterator begin_column(unsigned int column_number) const
Definition: YoungTab.hh:1453
in_row_const_iterator cbegin_row(unsigned int row_number) const
Definition: YoungTab.hh:1477
const_iterator cbegin() const
Definition: YoungTab.hh:1385
void projector(combin::symmetriser< T > &, bool modulo_monoterm=false) const
Definition: YoungTab.hh:1606
in_column_const_iterator cbegin_column(unsigned int column_number) const
Definition: YoungTab.hh:1431
virtual unsigned int number_of_rows() const
Definition: YoungTab.hh:1905
const_iterator cend() const
Definition: YoungTab.hh:1391
void sort_within_columns(StrictWeakOrdering comp)
Definition: YoungTab.hh:498
bool compare_without_multiplicity(const filled_tableau< T > &other) const
Definition: YoungTab.hh:428
filled_tableau< T > & operator=(const filled_tableau< T > &)
Definition: YoungTab.hh:1738
in_column_iterator begin_column(unsigned int column_number)
Definition: YoungTab.hh:1409
void sort_within_columns()
Definition: YoungTab.hh:476
iterator end()
Definition: YoungTab.hh:1378
in_row_const_iterator cend_row(unsigned int row_number) const
Definition: YoungTab.hh:1483
void canonicalise()
Sort equal-length columns and sort within columns.
Definition: YoungTab.hh:490
void copy_shape(const tableau &)
Definition: YoungTab.hh:418
std::pair< int, int > find(const T &) const
Definition: YoungTab.hh:464
std::vector< box_row > row_stack
Definition: YoungTab.hh:345
in_row_iterator begin_row(unsigned int row_number)
Definition: YoungTab.hh:1465
void sort_columns(StrictWeakOrdering comp)
Definition: YoungTab.hh:510
row_stack rows
Definition: YoungTab.hh:346
T & operator()(unsigned int row, unsigned int col)
Definition: YoungTab.hh:1918
const T & operator[](unsigned int boxnum) const
Definition: YoungTab.hh:1934
yngrat_t projector_normalisation() const
Definition: YoungTab.hh:1598
OutputIterator Garnir_set(OutputIterator, unsigned int, unsigned int) const
Definition: YoungTab.hh:1505
filled_tableau()
Definition: YoungTab.hh:1726
in_column_iterator end_column(unsigned int column_number)
Definition: YoungTab.hh:1418
in_row_const_iterator end_row(unsigned int row_number) const
Definition: YoungTab.hh:1495
iterator begin()
Definition: YoungTab.hh:1372
bool has_nullifying_trace() const
Definition: YoungTab.hh:434
void swap_columns(unsigned int c1, unsigned int c2)
Definition: YoungTab.hh:1970
std::pair< int, int > nonstandard_loc() const
Definition: YoungTab.hh:1529
in_column_const_iterator end_column(unsigned int column_number) const
Definition: YoungTab.hh:1459
in_column_const_iterator cend_column(unsigned int column_number) const
Definition: YoungTab.hh:1440
virtual unsigned int row_size(unsigned int row) const
Definition: YoungTab.hh:1911
virtual void clear()
Definition: YoungTab.hh:1992
filled_tableau(const filled_tableau< T > &)
Definition: YoungTab.hh:1732
virtual void add_box(unsigned int row)
Definition: YoungTab.hh:1952
const_iterator end() const
Definition: YoungTab.hh:1403
virtual void remove_box(unsigned int row)
Definition: YoungTab.hh:1982
in_row_const_iterator begin_row(unsigned int row_number) const
Definition: YoungTab.hh:1489
Definition: YoungTab.hh:47
unsigned long hook_length(unsigned int row, unsigned int col) const
Definition: YoungTab.cc:82
yngint_t hook_length_prod() const
Definition: YoungTab.cc:92
virtual ~tableau_base()
Definition: YoungTab.cc:31
virtual unsigned int number_of_rows() const =0
yngint_t dimension(unsigned int) const
Definition: YoungTab.cc:57
tableau_base()
Definition: YoungTab.cc:26
virtual void clear()=0
virtual unsigned int row_size(unsigned int row) const =0
virtual void add_row(unsigned int row_size)
Definition: YoungTab.cc:49
yngrat_t multiplicity
Definition: YoungTab.hh:59
virtual void add_box(unsigned int row)=0
int selfdual_column
Definition: YoungTab.hh:60
virtual unsigned int column_size(unsigned int col) const
Definition: YoungTab.cc:71
virtual void remove_box(unsigned int row)=0
Definition: YoungTab.hh:66
virtual unsigned int number_of_rows() const
Definition: YoungTab.cc:120
tableau & operator=(const tableau &)
Definition: YoungTab.cc:136
virtual unsigned int row_size(unsigned int row) const
Definition: YoungTab.cc:125
virtual void add_box(unsigned int row)
Definition: YoungTab.cc:101
virtual void clear()
Definition: YoungTab.cc:131
virtual void remove_box(unsigned int row)
Definition: YoungTab.cc:112
std::vector< int > rows
Definition: YoungTab.hh:80
virtual ~tableau()
Definition: YoungTab.cc:35
tableau()
Definition: YoungTab.cc:39
Definition: YoungTab.hh:350
std::list< T > tableau_container_t
Definition: YoungTab.hh:360
tableau_container_t storage
Definition: YoungTab.hh:361
void add_tableau(const T &)
Definition: YoungTab.hh:1581
bool standard_form()
Put the set of tableaux into standard form by using Garnir symmetries.
Definition: YoungTab.hh:1545
void symmetrise(const T &tabsym)
Definition: YoungTab.hh:393
std::back_insert_iterator< tableau_container_t > back_insert_iterator
Definition: YoungTab.hh:363
void remove_nullifying_traces()
Definition: YoungTab.hh:382
back_insert_iterator get_back_insert_iterator()
Definition: YoungTab.hh:376
yngint_t total_dimension(unsigned int dim)
Definition: YoungTab.hh:1746
std::vector< range_t > range_vector_t
Definition: Combinatorics.hh:40
unsigned long factorial(unsigned int x)
Definition: Combinatorics.cc:23
int ordersign(iterator1 b1, iterator1 e1, iterator2 b2, iterator2 e2, int stepsize=1)
Definition: Combinatorics.hh:224
Generic Young tableaux routines.
Definition: YoungTab.cc:24
void add_box(tableau &tab1, unsigned int row1, const tableau &, unsigned int, unsigned int)
Definition: YoungTab.cc:182
std::ostream & operator<<(std::ostream &str, const tableau &tab)
Definition: YoungTab.cc:142
bool legal_box(const std::vector< std::pair< int, int > > &prev, const std::vector< std::pair< int, int > > &ths, int colpos, int trypos)
filled_tableau< std::pair< int, int > > keeptrack_tab_t
Definition: YoungTab.hh:1782
void LR_tensor(const tableaux< T > &tabs1, const T &tab2, unsigned int maxrows, OutputIterator out, bool alltabs=false)
Definition: YoungTab.hh:1758
void LR_add_box(const Tab &tab2, Tab &newtab, unsigned int currow2, unsigned int curcol2, unsigned int startrow, unsigned int maxrows, OutputIterator outit, keeptrack_tab_t &Ycurrent, bool alltabs)
Definition: YoungTab.hh:1785