Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
Download

GAP 4.8.9 installation with standard packages -- copy to your CoCalc project to get it

563604 views
1
#include "typedef.h"
2
#include "matrix.h"
3
#include "idem.h"
4
#include "bravais.h"
5
#include "orbit.h"
6
#include "sort.h"
7
8
/*extern matrix_TYP ** orbit_alg();*/
9
10
/*Wahrscheinlich verursacht das Rechnen mit Matrizen, die nicht Ganzzahlig sind
11
Probleme. */
12
extern void free_tree(struct tree *p);
13
14
/* This function compares two matrices in lexicographic order.
15
It is supposed that they behave well (cols etc equal). */
16
static int cmp_mat_lex (matrix_TYP *A, matrix_TYP *B)
17
{
18
int i, j;
19
20
21
for (i=0; i<A->rows; i++)
22
for (j=0; j<A->cols; j++)
23
if (A->array.SZ[i][j] != B->array.SZ[i][j])
24
if (A->array.SZ[i][j] < B->array.SZ[i][j])
25
return -1;
26
else
27
return 1;
28
29
return 0;
30
}
31
32
static int hash_number(matrix_TYP *M)
33
{
34
int i,j,h;
35
int **SZ = M->array.SZ;
36
/*K: Wahrscheinlich weniger Arbeit fuer Rechner durch Einfueheren von
37
"Zwischenpointer"*/
38
h = 0;
39
for(i=0; i<M->rows; i++)
40
for(j=0; j<M->cols; j++)
41
h += SZ[i][j];
42
43
return h;
44
}
45
46
static void sort_cols (matrix_TYP *N)
47
{
48
49
int i, j, is_different, swap_cols;
50
51
for (i=1; i<N->cols; i++)
52
{
53
is_different = FALSE, swap_cols = FALSE;
54
55
for (j=0; j<N->rows && is_different == FALSE; j++)
56
if (N->array.SZ[j][i] > N->array.SZ[j][i-1])
57
is_different = TRUE;
58
else if (N->array.SZ[j][i] < N->array.SZ[j][i-1])
59
is_different = TRUE,
60
swap_cols = TRUE;
61
62
if (swap_cols)
63
{
64
col_per (N, i-1, i);
65
i = 0;
66
}
67
68
}
69
70
}
71
72
static void permute_and_sort (matrix_TYP *N, int number)
73
{
74
int i, j, k = 1;
75
matrix_TYP **set;
76
int used = -1, unused = 0;
77
78
if (number != 1)
79
{
80
for (i=2; i<=number; i++)
81
k *= i;
82
83
if ( (set = (matrix_TYP **) malloc ((k+1) * sizeof (matrix_TYP *))) == NULL)
84
{
85
perror ("set");
86
exit (2);
87
}
88
89
set [0] = copy_mat (N);
90
91
while (used < unused)
92
{
93
94
used ++;
95
96
set [unused + 1] = copy_mat (set [used]);
97
98
row_per (set [unused + 1], N->rows - number, N->rows - number + 1);
99
100
for (i=0; i<=unused && cmp_mat_lex (set [unused + 1], set [i]) != 0; i++)
101
;
102
103
104
if (i == unused + 1)
105
unused ++;
106
else
107
free_mat (set [unused + 1]);
108
109
110
111
set [unused + 1] = copy_mat (set [used]);
112
113
row_per (set [unused + 1], N->rows - number, N->rows - 1);
114
115
for (i=1; i <= number - 1; i++)
116
row_per (set [unused + 1], N->rows - i - 1, N->rows - i);
117
118
for (i=0; i<=unused && cmp_mat_lex (set [unused + 1], set [i]) != 0; i++)
119
;
120
121
if (i == unused + 1)
122
unused ++;
123
else
124
free_mat (set [unused + 1]);
125
126
}
127
128
129
for (i=0; i<=used; i++)
130
sort_cols (set[i]);
131
132
133
k = 0;
134
for (i=1; i<=used; i++)
135
if (cmp_mat_lex (set [k], set [i]) > 0)
136
k = i;
137
138
139
for (i=0; i<N->rows; i++)
140
for (j=0; j<N->cols; j++)
141
N->array.SZ [i][j] = set [k]->array.SZ [i][j];
142
143
for (i=0; i<=unused; i++)
144
free_mat (set [i]);
145
146
free (set);
147
}
148
else
149
{
150
sort_cols (N);
151
}
152
}
153
154
static int order(matrix_TYP *A)
155
{
156
157
int i = 1;
158
159
matrix_TYP *B;
160
161
B = copy_mat(A);
162
Check_mat(B);
163
164
while (! ( B->flags.Scalar && B->array.SZ[0][0] == 1)){
165
mat_muleq(B,A);
166
Check_mat(B);
167
i++;
168
}
169
170
free_mat(B);
171
return i;
172
}
173
174
matrix_TYP *compute_q_matrix (bravais_TYP *G)
175
{
176
matrix_TYP **Group, **Idem, **representant, **conjugacy_class, *REP;
177
matrix_TYP *I, *F, *output_mat;
178
matrix_TYP *waste, *waste2;
179
int orb_alg_options[6];
180
int group_order, *length_conj_class;
181
/* int reserved_conj_class = 0; */
182
int class_counter = 0;
183
int idem_no;
184
int i, j, h;
185
186
187
I = einheitsmatrix( G->dim );
188
F = rform(G->gen, G->gen_no, I, 101);
189
Idem = idempotente(G->gen, G->gen_no, F, &idem_no, &i, &j, NULL);
190
free_mat(F);
191
for (h=0; h<i+j; h++)
192
free_mat(Idem[idem_no+h]);
193
/* Here we free some Idem-elements that are not needed for our aims. */
194
195
/* As a first step compute the whole group out of the
196
Generators given by the "bravais_TYP *G".
197
This is done by getting the orbit of the unit element
198
under operation of the group.*/
199
200
orb_alg_options[0] = 0;
201
orb_alg_options[1] = 0;
202
orb_alg_options[2] = 0,
203
orb_alg_options[3] = 0,
204
orb_alg_options[4] = 0,
205
orb_alg_options[5] = 0;
206
207
Group = orbit_alg( I, G, NULL, orb_alg_options, &group_order);
208
mat_quicksort(Group, 0 , group_order - 1,mat_comp);
209
210
/* The next step simply consists in dividing the whole group into its
211
conjugacy classes. This is done by getting the orbit under conjugation
212
for every group element that has not yet been found to lie in another
213
conjugacy class.
214
Technically this is done by setting up a list "not_yet_found" that
215
contains a flag for every group element saying if it was already found.
216
Das Programm startet am Anfang der Liste der Gruppenelemente und berechnet
217
nach einander von ...*/
218
219
220
orb_alg_options[0] = 4;
221
orb_alg_options[1] = 0;
222
orb_alg_options[2] = 0;
223
orb_alg_options[3] = FALSE;
224
orb_alg_options[4] = 0;
225
orb_alg_options[5] = 0;
226
227
228
REP = orbit_representatives(Group,
229
group_order,
230
G,
231
orb_alg_options,
232
&class_counter,
233
1);
234
235
if ( (representant = (matrix_TYP **) malloc(class_counter * sizeof(matrix_TYP *)) ) == NULL)
236
{
237
perror ("representant");
238
exit (2);
239
}
240
241
for (i=0;i<class_counter;i++){
242
representant[i] = Group[REP->array.SZ[0][i]];
243
Group[REP->array.SZ[0][i]] = NULL;
244
}
245
length_conj_class = REP->array.SZ[1];
246
REP->array.SZ[1] = (int *) malloc(1*sizeof(int));
247
248
for(i=0; i<group_order; i++){
249
if (Group[i] != NULL) free_mat(Group[i]);
250
}
251
free(Group);
252
free_mat(REP);
253
254
output_mat = init_mat( 9 + idem_no, class_counter, "");
255
256
/* Achtung: Probleme bei nicht ganzzahligen Matrizen !!! */
257
258
/* Put the length of the conjugation classes into the 0-th row of the
259
output matrix. */
260
for( i=0; i<class_counter; i++)
261
output_mat->array.SZ[0][i] = length_conj_class[i];
262
free(length_conj_class);
263
264
/* Put the order of the representant into the 1-st row of the output matrix*/
265
for( i=0; i<class_counter; i++)
266
output_mat->array.SZ[1][i] = order( representant[i] );
267
268
/* Put the trace of the conjugation classes into the 2-nd row of the
269
output matrix. */
270
for( i=0; i<class_counter; i++)
271
output_mat->array.SZ[2][i] = trace( representant[i] );
272
273
274
/* Put the trace of the square of elements of every conjugation classes
275
into the 3-nd row of the output matrix. */
276
for( i=0; i<class_counter; i++)
277
{
278
waste = mat_mul( representant[i], representant[i]);
279
280
output_mat->array.SZ[3][i] = trace(waste);
281
282
free_mat(waste);
283
}
284
285
/* Put the trace of the cube of elements of every conjugation classes
286
into the 4-th row of the output matrix. */
287
for( i=0; i<class_counter; i++)
288
{
289
waste2 = mat_mul( representant[i], representant[i]);
290
waste = mat_mul( waste2, representant[i] );
291
292
output_mat->array.SZ[4][i] = trace( waste );
293
294
free_mat(waste);
295
free_mat(waste2);
296
}
297
298
/* Get the rank of the fixspace of every element */
299
for (i=0; i<class_counter; i++)
300
{
301
waste = copy_mat( representant[i] );
302
303
for (j=0; j<I->rows; j++)
304
waste->array.SZ[j][j]--; /* This means: matrix minus identity */
305
306
Check_mat( waste );
307
output_mat->array.SZ[5][i] = tgauss( waste );
308
free_mat( waste );
309
}
310
311
/* Compute the rank of the antifixspace of every element. */
312
for (i=0; i<class_counter; i++)
313
{
314
waste = copy_mat( representant[i] );
315
316
for (j=0; j<I->rows; j++)
317
waste->array.SZ[j][j]++;/* This means: matrix plus identity */
318
319
Check_mat( waste );
320
output_mat->array.SZ[6][i] = tgauss( waste );
321
free_mat( waste );
322
}
323
324
/* get the rank of (x-1)^2 */
325
for (i=0; i<class_counter; i++)
326
{
327
waste = copy_mat( representant[i] );
328
for (j=0; j<I->rows; j++)
329
waste->array.SZ[j][j]--;
330
331
Check_mat( waste );
332
mat_muleq(waste,waste);
333
Check_mat( waste );
334
output_mat->array.SZ[7][i] = tgauss( waste );
335
free_mat( waste );
336
}
337
338
/* put the rank of (x+1)^2 into the 8-th row of the output_mat*/
339
for (i=0; i<class_counter; i++)
340
{
341
waste = copy_mat( representant[i] );
342
343
for (j=0; j<I->rows; j++)
344
waste->array.SZ[j][j]++;
345
346
Check_mat( waste );
347
mat_muleq( waste, waste );
348
Check_mat( waste );
349
output_mat->array.SZ[8][i] = tgauss( waste );
350
free_mat( waste );
351
}
352
353
/* Write into the 9-th row of output_mat the trace of idem??? */
354
for (i=0; i<class_counter; i++)
355
for (j=0; j<idem_no; j++)
356
{
357
waste = mat_mul(Idem[j],representant[i]);
358
output_mat->array.SZ[9+j][i] = trace(waste)/waste->kgv;
359
free_mat(waste);
360
}
361
for(i=0; i<idem_no; i++)
362
free_mat(Idem[i]);
363
free(Idem);
364
365
/* The matrix has now to be ordered by shuffling columns and rows. */
366
permute_and_sort (output_mat, idem_no);
367
368
369
370
371
free_mat(I);
372
373
for(i=0; i<class_counter; i++)
374
free_mat(representant[i]);
375
free(representant);
376
377
return output_mat;
378
}
379
380