This file is indexed.

/usr/share/gap/lib/grpnames.gd is in gap-libs 4r7p9-1.

This file is owned by root:root, with mode 0o644.

The actual contents of the file can be viewed below.

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
#############################################################################
##
#W  grpnames.gd                                                   Stefan Kohl
##                                                             Markus Püschel
##                                                            Sebastian Egner
##
##
#Y  Copyright (C) 2004 The GAP Group
##
##  This file contains declarations of attributes, operations and functions
##  related to the determination of structure descriptions for finite groups.
##
##  It also includes comments from corresponding GAP3 code written by
##  Markus Püschel and Sebastian Egner.
##

#############################################################################
##
#A  DirectFactorsOfGroup( <G> ) . . . . . decomposition into a direct product
##
##  <ManSection>
##  <Attr Name="DirectFactorsOfGroup" Arg="G"/>
##
##  <Description>
##    A sorted list of factors [<A>G1</A>, .., <A>Gr</A>] such that
##    <A>G</A> = <A>G1</A> x .. x <A>Gr</A> and none of the <A>Gi</A>
##    is a direct product.
##  </Description>
##  </ManSection>
##
##  The following hold:
##
##    (1) <Gi> is a normal subgroup of <G>.
##    (2) <i> <= <j> ==> Size(<Gi>) <= Size(<Gj>).
##    (3) Size(<Gi>) > 1 unless <r> = 1 and <G> = 1.
##    (4) <G> = <G1> * .. * <Gr> as the complex product.
##    (5) $Gi \cap (G1 * .. * G_{i-1} * G_{i+1} * .. * Gr) = 1$.
##
##  Factorization of a permutation group into a direct product 
##  ==========================================================
##
##  Def.: Seien G1, .., Gr endliche Gruppen, dann ist
##        G := (G1 x .. x Gr, *) eine Gruppe mit der Operation
##          (g1, .., gr)*(h1, .., hr) := (g1 h1, .., gr hr).
##        Wir sagen dann G ist das ("au"sere) direkte Produkt
##        der Gruppen G1, .., Gr und schreiben G = G1 x .. x Gr.
##
##  Lemma: Seien G1, .., Gr Normalteiler der endlichen Gruppe G
##         mit den Eigenschaften
##           (1) |G| = |G1| * .. * |Gr|
##           (2) |Gi meet (Gi+1 * .. * Gr)| = 1
##         Dann ist G = G1 x .. x Gr.
##  Bew.:  M. Hall, Th. 2.5.2.
##
##  Lemma: Seien G = G1 x .. x Gr = H1 x .. x Hs zwei Zerlegungen
##         von G in direkt unzerlegbare Faktoren. Dann gilt
##         (1) r = s
##         (2) Es gibt ein Permutation p der Faktoren, so
##             da"s G[i] ~= H[p(i)] f"ur alle i.
##  Bew.: Satz von Krull-Remak-Schmidt, Huppert I.
##
##  Statements needed for DirectFactorsGroup
##  ========================================
##
##  Lemma:
##  If G1, G2 are normal subgroups in G and (G1 meet G2) = 1
##  then G = G1 x G2 <==> |G| = |G1|*|G2|.
##  Proof:
##    "==>": trivial.
##    "<==": Use G1*G2/G1 ~= G2/(G1 meet G2) = G2/1 ==>
##           |G1*G2|/|G1| = |G2|/|1|. q.e.d.
##
##  Remark:
##   The normal subgroup lattice of G does not contain
##   all the information needed for the normal subgroup lattice
##   of G2 for a decomposition G = G1 x G2. However let 
##   G = G1 x .. x Gr be finest direct product decomposition
##   then all Gi are normal subgroups in G. Thus all Gi occur in
##   the set NormalSubgroups(G) and we may split G recursively 
##   without recomputing normal subgroup lattices for factors.
##
##  Method to enumerate factorizations given the divisors:
##   Consider a strictly increasing chain
##     1  <  a1 < a2 < .. < a_n  <  A
##   of positive divisors of an integer A. 
##   The task is to enumerate all pairs 1 <= i <= j <= n
##   such that a_i*a_j = A. This is done by
##
##   i := 1;  
##   j := n;
##   while i <= j do                   
##     while j > i and a_i*a_j > A do 
##       j := j-1; 
##     end while;
##     if a_i*a_j = A then
##       "found i <= j with a_i*a_j = A"
##     end if;
##     i := i+1;
##   end while;
##
##   which is based on the following fact:
##   Lemma:
##      Let i1 <= j1, i2 <= j2 be such that 
##      a_i1*a_j1 = a_i2*a_j2 = A, then
##        i2 > i1 ==> j2 < j1.
##   Proof:
##      i2 > i1 
##      ==> a_i2 > a_i1  by strictly increasing a's
##      ==> a_i1*a_j1 = A = a_i2*a_j2 > a_i1*a_j2 by *a_j2
##      ==> a_j1 > a_j2 by /a_i1
##      ==> j1 > j2. q.e.d
##
##   Now consider two strictly increasing chains
##     1 <= a1 < a2 < .. < a_n <= A
##     1 <= b1 < b2 < .. < b_m <= A
##   of positive divisors of an integer A.
##   The task is to enumerate all pairs i, j with
##   1 <= i <= n, 1 <= j <= m such that a_i*b_j = A.
##      This is done by merging the two sequences into
##   a single increasing sequence of pairs <c_i, which_i>
##   where which_i indicates where c_i is in the a-sequence
##   and where it is in the b-sequence if any. The the
##   linear algorithm above may be used.
##
DeclareAttribute( "DirectFactorsOfGroup", IsGroup );

#############################################################################
##
#A  SemidirectFactorsOfGroup( <G> ) . decomposition into a semidirect product
##
##  <ManSection>
##  <Attr Name="SemidirectFactorsOfGroup" Arg="G"/>
##
##  <Description>
##    A list [[<A>H1</A>, <A>N1</A>], .., [<A>Hr</A>, <A>Nr</A>]] of all
##    direct or semidirect decompositions with minimal <A>H</A>:
##    <A>G</A> = <A>Hi</A> semidirect <A>Ni</A> and |<A>Hi</A>| = |<A>Hj</A>|
##    is minimal with respect to all semidirect products.
##    Note that this function also recognizes direct products.
##  </Description>
##  </ManSection>
##
##  Literatur:
##    [1] Huppert Bd. I, Springer 1983.
##    [2] M. Hall: Theory of Groups. 2nd ed., 
##        Chelsea Publ. Co., 1979 NY.
##
##  Zerlegung eines semidirekten Produkts, Grundlagen
##  =================================================
##
##  Def.: Seien H, N Gruppen und f: H -> Aut(N) ein Gr.-Hom.
##        Dann wird G := (H x N, *) eine Gruppe mit der Operation
##        (h1, n1)*(h2, n2) := (h1 h2, f(h2)(n1)*n2).
##        Wir nennen G das ("au"sere) semidirekte Produkt von H und N
##        und schreiben G = H semidirect[f] N.
##
##  Lemma1:
##    Sei G eine endliche Gruppe, N ein Normalteiler und H eine
##    Untergruppe von G mit den Eigenschaften
##      (1) |H| * |N| = |G| und
##      (2) |H meet N| = 1.
##    Dann gibt es ein f mit G = H semidirect[f] N.
##  Bew.: [2], Th. 6.5.3. 
##
##  Lemma2:
##    Sei G = H semidirect[phi] N und h in H, n in N, dann ist auch
##    G = H^(h n) semidirect[psi] N mit
##    psi = inn_n o phi o inn_h^-1 o inn_n^-1.
##  Bew.:
##    1. |H^(h n)| = |H| ==> |H^(h n)|*|N| = |G| und
##       |H^(h n) meet N| = 1 <==> |H meet N| = 1, weil N normal ist.
##       Daher ist G = H^(h n) semidirect[psi] N mit einem
##       psi : H^(h n) -> Aut(N).
##    2. Das psi ist durch H und N eindeutig bestimmt.
##    3. Die Form von psi wie oben angegeben kann durch berechnen
##       von psi(h)(n) nachgepr"uft werden.
##
DeclareAttribute( "SemidirectFactorsOfGroup", IsGroup );

#############################################################################
##
#A  DecompositionTypesOfGroup( <G> ) . .  descriptions of decomposition types
#A  DecompositionTypes( <G> )
##
##  <ManSection>
##  <Attr Name="DecompositionTypesOfGroup" Arg="G"/>
##  <Attr Name="DecompositionTypes" Arg="G"/>
##
##  <Description>
##    A list of all possible decomposition types of the group
##    into direct/semidirect products of non-splitting factors. <P/>
##
##    A <E>decomposition type</E> <A>type</A> is denoted by a specification
##    of the form
##    <Log><![CDATA[
##    <type> ::= 
##      <integer>                 ; cyclic group of prime power order
##    | ["non-split", <integer>]  ; non-split extension; size annotated
##    | ["x", <type>, .., <type>] ; non-trivial direct product (ass., comm.)
##    | [":", <type>, <type>]     ; non-direct, non-trivial split extension
##    ]]></Log>
##  </Description>
##  </ManSection>
##
DeclareAttribute( "DecompositionTypesOfGroup", IsGroup );
DeclareSynonym( "DecompositionTypes", DecompositionTypesOfGroup );

#############################################################################
##
#P  IsDihedralGroup( <G> )
#A  DihedralGenerators( <G> )
##
##  <ManSection>
##  <Prop Name="IsDihedralGroup" Arg="G"/>
##  <Attr Name="DihedralGenerators" Arg="G"/>
##
##  <Description>
##    Indicates whether the group <A>G</A> is a dihedral group.
##    If it is, methods may set the attribute <C>DihedralGenerators</C> to
##    [<A>t</A>,<A>s</A>], where <A>t</A> and <A>s</A> are two elements such
##    that <A>G</A> = <M><A>t, s | t^2 = s^n = 1, s^t = s^-1</A></M>.
##  </Description>
##  </ManSection>
##
DeclareProperty( "IsDihedralGroup", IsGroup );
DeclareAttribute( "DihedralGenerators", IsGroup );

#############################################################################
##
#P  IsQuaternionGroup( <G> )
#A  QuaternionGenerators( <G> )
##
##  <ManSection>
##  <Prop Name="IsQuaternionGroup" Arg="G"/>
##  <Attr Name="QuaternionGenerators" Arg="G"/>
##
##  <Description>
##    Indicates whether the group <A>G</A> is a generalized quaternion group 
##    of size <M>N = 2^(k+1)</M>, <M>k >= 2</M>. If it is, methods may set
##    the attribute <C>QuaternionGenerators</C> to [<A>t</A>,<A>s</A>],
##    where <A>t</A> and <A>s</A> are two elements such that <A>G</A> =
##    <M><A>t, s | s^(2^k) = 1, t^2 = s^(2^k-1), s^t = s^-1</A></M>.
##  </Description>
##  </ManSection>
##
DeclareProperty( "IsQuaternionGroup", IsGroup );
DeclareAttribute( "QuaternionGenerators", IsGroup );

#############################################################################
##
#P  IsQuasiDihedralGroup( <G> )
#A  QuasiDihedralGenerators( <G> )
##
##  <ManSection>
##  <Prop Name="IsQuasiDihedralGroup" Arg="G"/>
##  <Attr Name="QuasiDihedralGenerators" Arg="G"/>
##
##  <Description>
##    Indicates whether the group <A>G</A> is a quasidihedral group 
##    of size <M>N = 2^(k+1)</M>, <M>k >= 2</M>. If it is, methods may set
##    the attribute <C>QuasiDihedralGenerators</C> to [<A>t</A>,<A>s</A>],
##    where <A>t</A> and <A>s</A> are two elements such that <A>G</A> =
##    <M><A>t, s | s^(2^k) = t^2 = 1, s^t = s^(-1 + 2^(k-1))</A></M>.
##  </Description>
##  </ManSection>
##
DeclareProperty( "IsQuasiDihedralGroup", IsGroup );
DeclareAttribute( "QuasiDihedralGenerators", IsGroup );

#############################################################################
##
#P  IsPSL( <G> )
##
##  <ManSection>
##  <Prop Name="IsPSL" Arg="G"/>
##
##  <Description>
##    Indicates whether the group <A>G</A> is isomorphic to the projective
##    special linear group PSL(<A>n</A>,<A>q</A>) for some integer <A>n</A>
##    and some prime power <A>q</A>. If it is, methods may set the attribute
##    <C>ParametersOfGroupViewedAsPSL</C>.
##  </Description>
##  </ManSection>
##
DeclareProperty( "IsPSL", IsGroup );

#############################################################################
##
#A  ParametersOfGroupViewedAsPSL 
#A  ParametersOfGroupViewedAsSL  
#A  ParametersOfGroupViewedAsGL
##
##  triples (n,p,e) such that the group is isomorphic to PSL(n,p^e), SL(n,p^e) 
##  and GL(n,p^e) respectively
##
##  <ManSection>
##  <Attr Name="ParametersOfGroupViewedAsPSL" Arg="G"/>
##  <Attr Name="ParametersOfGroupViewedAsSL" Arg="G"/>
##  <Attr Name="ParametersOfGroupViewedAsGL" Arg="G"/>
##
##  <Description>
##  </Description>
##  </ManSection>
##
DeclareAttribute( "ParametersOfGroupViewedAsPSL", IsGroup );
DeclareAttribute( "ParametersOfGroupViewedAsSL", IsGroup );
DeclareAttribute( "ParametersOfGroupViewedAsGL", IsGroup );

#############################################################################
##
#A  AlternatingDegree . . . .  degree of isomorphic natural alternating group
#A  SymmetricDegree . . . . . .  degree of isomorphic natural symmetric group
#A  PSLDegree . . . . . .  (one possible) degree of an isomorphic natural PSL
#A  PSLUnderlyingField . . (one possible) underlying field   "      "      "
#A  SLDegree  . . . . . .  (one possible) degree of an isomorphic natural SL
#A  SLUnderlyingField . .  (one possible) underlying field   "      "      "
#A  GLDegree  . . . . . .  (one possible) degree of an isomorphic natural GL
#A  GLUnderlyingField . .  (one possible) underlying field   "      "      "
##
##  <Attr Name="AlternatingDegree" Arg="G"/>
##  <Attr Name="SymmetricDegree" Arg="G"/>
##  <Attr Name="PSLDegree" Arg="G"/>
##  <Attr Name="PSLUnderlyingField" Arg="G"/>
##  <Attr Name="SLDegree" Arg="G"/>
##  <Attr Name="SLUnderlyingField" Arg="G"/>
##  <Attr Name="GLDegree" Arg="G"/>
##  <Attr Name="GLUnderlyingField" Arg="G"/>
##
##  <Description>
##  </Description>
##  </ManSection>
##
DeclareAttribute( "AlternatingDegree", IsGroup );
DeclareAttribute( "SymmetricDegree", IsGroup );
DeclareAttribute( "PSLDegree", IsGroup );
DeclareAttribute( "PSLUnderlyingField", IsGroup );
DeclareAttribute( "SLDegree", IsGroup );
DeclareAttribute( "SLUnderlyingField", IsGroup );
DeclareAttribute( "GLDegree", IsGroup );
DeclareAttribute( "GLUnderlyingField", IsGroup );

#############################################################################
##
#F  SizeGL(  <n>, <q> )
#F  SizeSL(  <n>, <q> )
#F  SizePSL( <n>, <q> )
##
##  <ManSection>
##  <Func Name="SizeGL" Arg="n, q"/>
##  <Func Name="SizeSL" Arg="n, q"/>
##  <Func Name="SizePSL" Arg="n, q"/>
##
##  <Description>
##    Computes the size of the group GL(<A>n</A>,<A>p</A>^<A>e</A>),
##    SL(<A>n</A>,<A>p</A>^<A>e</A>) or PSL(<A>n</A>,<A>p</A>^<A>e</A>),
##    respectively.
##  </Description>
##  </ManSection>
##
##  The following formulas are used:
##
##      |GL(n, p, e)|  = Product(p^(e n) - p^(e k) : k in [0..n-1])
##      |SL(n, p, e)|  = |GL(n, p, e)| / (p^e - 1)
##      |PSL(n, p, e)| = |SL(n, p, e)| / gcd(p^e - 1, n)
##  
DeclareGlobalFunction( "SizeGL" );
DeclareGlobalFunction( "SizeSL" );
DeclareGlobalFunction( "SizePSL" );

#############################################################################
##
#F  LinearGroupParameters( <N> )
##
##  <ManSection>
##  <Func Name="LinearGroupParameters" Arg="N"/>
##
##  <Description>
##    Determines all parameters <A>n</A> >= 2, <A>p</A> prime, <A>e</A> >= 1,
##    such that the given number is the size of one of the linear groups
##    GL(<A>n</A>,<A>p</A>^<A>e</A>), SL(<A>n</A>,<A>p</A>^<A>e</A>) or
##    PSL(<A>n</A>,<A>p</A>^<A>e</A>). <P/>
##    A record with the fields <C>npeGL</C>, <C>npeSL</C>, <C>npePSL</C> is
##    returned, which contains the lists of possible triples
##    [<A>n</A>,<A>p</A>,<A>e</A>].
##  </Description>
##  </ManSection>
##
##  Lemma (o.B.):
##  Es bezeichne 
##
##    gl(n, p, e)  = Product(p^(e n) - p^(e k) : k in [0..n-1])
##    sl(n, p, e)  = gl(n, p, e) / (p^e - 1)
##    psl(n, p, e) = sl(n, p, e) / gcd(p^e - 1, n)
##
##  die Gr"o"sen der Gruppen GL, SL, PSL mit den Parametern
##  n, p, e. Dann gilt
##
##    gl(n, p, e)  = sl(n, p, e)  <==>  p^e = 2
##    sl(n, p, e)  = psl(n, p, e) <==>  gcd(p^e - 1, n) = 1
##    psl(n, p, e) = gl(n, p, e)  <==>  p^e = 2
##
##  und in diesen F"allen sind die dazugeh"origen Gruppen auch
##  isomorph. Dar"uberhinaus existieren genau die folgenden
##  sporadischen "Ubereinstimmungen
##  
##    psl(2, 2, 2) = psl(2, 5, 1) = 60    ; PSL(2, 4) ~= PSL(2, 5) ~= A5
##    psl(2, 7, 1) = psl(3, 2, 1) = 168   ; PSL(2, 7) ~= PSL(3, 2)
##    psl(4, 2, 1) = psl(3, 2, 2) = 20160 ; PSL(4, 2) not~= PSL(3, 4)
##   
##  wobei in den ersten beiden F"allen die dazugeh"origen Gruppen 
##  isomorph sind, im letzten Fall aber nicht! Die Gruppen PSL(4, 2)
##  und PSL(3, 4) sind "uber das Zentrum ihrer 2-Sylowgruppen
##  unterscheidbar (Huppert: S.185). 
##  Es bezeichne Z1, Z2 die Zentren der 2-Sylowgruppen von PSL(4, 2)
##  bzw. PSL(3, 4). Dann ist |Z1| = 2 und |Z2| = 4.
##
##  Die Aussage des Lemmas wurde rechnerisch bis zur Gruppenordnung 10^100
##  getestet.
##
DeclareGlobalFunction( "LinearGroupParameters" );

#############################################################################
##
#A  StructureDescription( <G> )
##
##  <#GAPDoc Label="StructureDescription">
##  <ManSection>
##  <Attr Name="StructureDescription" Arg="G"/>
##
##  <Description>
##  The method for <Ref Func="StructureDescription"/> exhibits a structure
##  of the given group <A>G</A> to some extent, using the strategy outlined
##    below. The idea is to return a possibly short string which gives some
##    insight in the structure of the considered group. It is intended
##  primarily for small groups (order less than 100) or groups with few normal
##  subgroups, in other cases, in particular large <M>p</M>-groups, it can
##  be very costly. Furthermore, the string returned is -- as the action on
##  chief factors is not described -- often not the most useful way to describe
##  a group.<P/>
##
##  The string returned by <Ref Func="StructureDescription"/> is
##  <B>not</B> an isomorphism invariant: non-isomorphic groups can have the
##  same string value, and two isomorphic groups in different representations
##  can produce different strings.
##
##  The value returned by <Ref Func="StructureDescription"/> is a string of
##  the following form: <P/>
##  <Listing><![CDATA[
##    StructureDescription(<G>) ::=
##        1                                 ; trivial group 
##      | C<size>                           ; cyclic group
##      | A<degree>                         ; alternating group
##      | S<degree>                         ; symmetric group
##      | D<size>                           ; dihedral group
##      | Q<size>                           ; quaternion group
##      | QD<size>                          ; quasidihedral group
##      | PSL(<n>,<q>)                      ; projective special linear group
##      | SL(<n>,<q>)                       ; special linear group
##      | GL(<n>,<q>)                       ; general linear group
##      | PSU(<n>,<q>)                      ; proj. special unitary group
##      | O(2<n>+1,<q>)                     ; orthogonal group, type B
##      | O+(2<n>,<q>)                      ; orthogonal group, type D
##      | O-(2<n>,<q>)                      ; orthogonal group, type 2D
##      | PSp(2<n>,<q>)                     ; proj. special symplectic group
##      | Sz(<q>)                           ; Suzuki group
##      | Ree(<q>)                          ; Ree group (type 2F or 2G)
##      | E(6,<q>) | E(7,<q>) | E(8,<q>)    ; Lie group of exceptional type
##      | 2E(6,<q>) | F(4,<q>) | G(2,<q>)
##      | 3D(4,<q>)                         ; Steinberg triality group
##      | M11 | M12 | M22 | M23 | M24
##      | J1 | J2 | J3 | J4 | Co1 | Co2
##      | Co3 | Fi22 | Fi23 | Fi24' | Suz
##      | HS | McL | He | HN | Th | B
##      | M | ON | Ly | Ru                  ; sporadic simple group
##      | 2F(4,2)'                          ; Tits group
##      | PerfectGroup(<size>,<id>)         ; the indicated group from the
##                                          ; library of perfect groups
##      | A x B                             ; direct product
##      | N : H                             ; semidirect product
##      | C(G) . G/C(G) = G' . G/G'         ; non-split extension
##                                          ; (equal alternatives and
##                                          ; trivial extensions omitted)
##      | Phi(G) . G/Phi(G)                 ; non-split extension:
##                                          ; Frattini subgroup and
##                                          ; Frattini factor group
##  ]]></Listing>
##  <P/>
##  Note that the <Ref Func="StructureDescription"/> is only <E>one</E>
##  possible way of building up the given group from smaller pieces. <P/>
##
##  The option <Q>short</Q> is recognized - if this option is set, an
##  abbreviated output format is used (e.g. <C>"6x3"</C> instead of
##  <C>"C6 x C3"</C>). <P/>
##
##  If the <Ref Func="Name"/> attribute is not bound, but
##  <Ref Func="StructureDescription"/> is, <Ref Func="View"/> prints the
##  value of the attribute <Ref Func="StructureDescription"/>.
##  The <Ref Func="Print"/>ed representation of a group is not affected
##  by computing a <Ref Func="StructureDescription"/>. <P/>
##
##  The strategy used to compute a <Ref Func="StructureDescription"/> is
##  as follows:
##  <P/>
##  <List>
##  <Mark>1.</Mark>
##  <Item>
##    Lookup in a precomputed list, if the order of <A>G</A> is not
##    larger than 100 and not equal to 64.
##  </Item>
##  <Mark>2.</Mark>
##  <Item>
##    If <A>G</A> is abelian, then decompose it into cyclic factors
##    in <Q>elementary divisors style</Q>. For example,
##    <C>"C2 x C3 x C3"</C> is <C>"C6 x C3"</C>.
##  </Item>
##  <Mark>3.</Mark>
##  <Item>
##    Recognize alternating groups, symmetric groups,
##    dihedral groups, quasidihedral groups, quaternion groups,
##    PSL's, SL's, GL's and simple groups not listed so far
##    as basic building blocks.
##  </Item>
##  <Mark>4.</Mark>
##  <Item>
##    Decompose <A>G</A> into a direct product of irreducible factors.
##  </Item>
##  <Mark>5.</Mark>
##  <Item>
##    Recognize semidirect products <A>G</A>=<M>N</M>:<M>H</M>,
##    where <M>N</M> is normal.
##    Select a pair <M>N</M>, <M>H</M> with the following preferences:
##    <List>
##    <Mark>1.</Mark>
##    <Item>
##      <M>H</M> is abelian
##    </Item>
##    <Mark>2.</Mark>
##    <Item>
##      <M>N</M> is abelian
##    </Item>
##    <Mark>2a.</Mark>
##    <Item>
##      <M>N</M> has many abelian invariants
##    </Item>
##    <Mark>3.</Mark>
##    <Item>
##      <M>N</M> is a direct product
##    </Item>
##    <Mark>3a.</Mark>
##    <Item>
##      <M>N</M> has many direct factors
##    </Item>
##    <Mark>4.</Mark>
##    <Item>
##      <M>\phi: H \rightarrow</M> Aut(<M>N</M>), 
##      <M>h \mapsto (n \mapsto n^h)</M> is injective.
##    </Item>
##    </List>
##  </Item>
##  <Mark>6.</Mark>
##  <Item>
##    Fall back to non-splitting extensions:
##    If the centre or the commutator factor group is non-trivial,
##    write <A>G</A> as Z(<A>G</A>).<A>G</A>/Z(<A>G</A>) or
##    <A>G</A>'.<A>G</A>/<A>G</A>', respectively.
##    Otherwise if the Frattini subgroup is non-trivial, write <A>G</A>
##    as <M>\Phi</M>(<A>G</A>).<A>G</A>/<M>\Phi</M>(<A>G</A>).
##  </Item>
##  <Mark>7.</Mark>
##  <Item>
##    If no decomposition is found (maybe this is not the case for
##    any finite group), try to identify <A>G</A> in the perfect groups
##    library. If this fails also, then return a string describing this
##    situation.
##  </Item>
##  </List>
##  Note that <Ref Func="StructureDescription"/> is <E>not</E> intended
##  to be a research tool, but rather an educational tool. The reasons for
##  this are as follows:
##  <List>
##    <Mark>1.</Mark>
##    <Item>
##      <Q>Most</Q> groups do not have <Q>nice</Q> decompositions.
##      This is in some contrast to what is often taught in elementary
##      courses on group theory, where it is sometimes suggested that
##      basically every group can be written as iterated direct or
##      semidirect product of cyclic groups and nonabelian simple groups.
##    </Item>
##    <Mark>2.</Mark>
##    <Item>
##      In particular many <M>p</M>-groups have very <Q>similar</Q>
##      structure, and <Ref Func="StructureDescription"/> can only
##      exhibit a little of it. Changing this would likely make the
##      output not essentially easier to read than a pc presentation.
##    </Item>
##  </List>
##  <Example><![CDATA[
##  gap> l := AllSmallGroups(12);;
##  gap> List(l,StructureDescription);; l;
##  [ C3 : C4, C12, A4, D12, C6 x C2 ]
##  gap> List(AllSmallGroups(40),G->StructureDescription(G:short));
##  [ "5:8", "40", "5:8", "5:Q8", "4xD10", "D40", "2x(5:4)", "(10x2):2", 
##    "20x2", "5xD8", "5xQ8", "2x(5:4)", "2^2xD10", "10x2^2" ]
##  gap> List(AllTransitiveGroups(DegreeAction,6),
##  >         G->StructureDescription(G:short));
##  [ "6", "S3", "D12", "A4", "3xS3", "2xA4", "S4", "S4", "S3xS3", 
##    "(3^2):4", "2xS4", "A5", "(S3xS3):2", "S5", "A6", "S6" ]
##  gap> StructureDescription(PSL(4,2));
##  "A8"
##  ]]></Example>
##  </Description>
##  </ManSection>
##  <#/GAPDoc>
##
DeclareAttribute( "StructureDescription", IsGroup );

#############################################################################
##
#E