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

563595 views
1
#include "typedef.h"
2
#include "longtools.h"
3
#include "longtools.h"
4
#include "matrix.h"
5
#include "orbit.h"
6
#include "idem.h"
7
#include "datei.h"
8
9
extern int INFO_LEVEL;
10
11
/******************************************************************************
12
@
13
@------------------------------------------------------------------------------
14
@ FILE: v4_catalog.c
15
@------------------------------------------------------------------------------
16
@
17
*******************************************************************************/
18
19
/******************************************************************************
20
@
21
@------------------------------------------------------------------------------
22
@
23
@ static matrix_TYP *test_v4(bravais_TYP *G)
24
@
25
@ Tests whether the given Bravais group G is isomorphic to V_4 = C_2 x C_2.
26
@ The order of the group has to be 4, and this order has to sit in G->order.
27
@
28
@ The return is NULL if the group is not isomophic to V_4, and otherwise
29
@ a matrix with non negative trace in G.
30
@------------------------------------------------------------------------------
31
@
32
*******************************************************************************/
33
static matrix_TYP *test_v4(bravais_TYP *G)
34
{
35
static int i,
36
j,
37
opt[6];
38
39
matrix_TYP **ELE,
40
*ID,
41
*TMP,
42
*g;
43
44
if (G->order != 4){
45
return NULL;
46
}
47
48
opt[2] = 4;
49
j = 0;
50
51
/* calculate all elements */
52
ID = init_mat(G->dim,G->dim,"1");
53
ELE = orbit_alg(ID,G,NULL,opt,&i);
54
55
for (i=0;i<4;i++){
56
TMP = mat_mul(ELE[i],ELE[i]);
57
if (mat_comp(ID,TMP)==0)
58
j++;
59
free_mat(TMP);
60
}
61
62
g = NULL;
63
64
/* all elements should have order at most 2 */
65
if (j==4){
66
for (i=0;i<4 && g == NULL; i++){
67
j = trace(ELE[i]);
68
if ((0<=j) && (j <G->dim)){
69
g = ELE[i];
70
ELE[i] = NULL;
71
}
72
}
73
}
74
75
/* clean up */
76
for (i=0;i<4;i++){
77
if (ELE[i] != NULL) free_mat(ELE[i]);
78
}
79
free(ELE);
80
81
free_mat(ID);
82
83
return g;
84
}
85
86
/******************************************************************************
87
@
88
@------------------------------------------------------------------------------
89
@
90
@ static matrix_TYP *basis_part(matrix_TYP *g, matrix_TYP *h,
91
@ matrix_TYP **plse,int rank2,int eps)
92
@
93
@------------------------------------------------------------------------------
94
@
95
*******************************************************************************/
96
static matrix_TYP *basis_part(matrix_TYP *g, matrix_TYP *h,
97
matrix_TYP **plse,int rank2,int eps)
98
{
99
100
int i,
101
j,
102
k,
103
old_rank,
104
rank;
105
106
matrix_TYP *E,
107
*A,
108
**tmp,
109
*tmp2,
110
*zass_mat,
111
*RES;
112
113
/* calculate a Z-basis for the eigen space of 0 */
114
tmp = long_solve_mat(h,NULL);
115
E = tmp[1];
116
free(tmp);
117
118
/* avoid trouble if there isn't any psle.. */
119
if (rank2 == 0){
120
return E;
121
}
122
123
/* calculate a Z-basis for the intersection E ^ (e1 + (eps) * g e1 .....) */
124
zass_mat = init_mat(rank2,2*g->cols,"");
125
for (i=0;i<rank2;i++){
126
tmp2 = mat_mul(g,plse[i]);
127
for (j=0;j<g->cols;j++){
128
zass_mat->array.SZ[i][j] = plse[i]->array.SZ[j][0]
129
+ eps * tmp2->array.SZ[j][0];
130
zass_mat->array.SZ[i][j+g->cols] = zass_mat->array.SZ[i][j];
131
}
132
free_mat(tmp2);
133
}
134
tmp2 = long_rein_mat(zass_mat);
135
free_mat(zass_mat);
136
zass_mat = tmp2;
137
tmp2 = NULL;
138
old_rank = zass_mat->rows;
139
real_mat(zass_mat,zass_mat->rows+E->cols,zass_mat->cols);
140
for (i=0;i<E->cols;i++){
141
for (j=0;j<E->rows;j++){
142
zass_mat->array.SZ[old_rank+i][j] = E->array.SZ[j][i];
143
}
144
}
145
long_row_hnf(zass_mat);
146
147
rank = -1;
148
i = -1;
149
while (rank == -1){
150
i++;
151
rank = i;
152
for (j=0;j<g->cols;j++)
153
if (zass_mat->array.SZ[i][j] != 0){
154
rank = -1;
155
}
156
}
157
158
tmp2 = init_mat(zass_mat->rows-rank,g->cols,"");
159
for (i=0;i<zass_mat->rows-rank;i++){
160
for (j=0;j<g->cols;j++){
161
tmp2->array.SZ[i][j] = zass_mat->array.SZ[i+rank][j+g->cols];
162
}
163
}
164
free_mat(zass_mat);
165
zass_mat = long_rein_mat(tmp2);
166
free_mat(tmp2);
167
tmp2 = zass_mat;
168
zass_mat=NULL;
169
170
/* now add vectors to give a Z-basis of E */
171
/* represent the rows of tmp2 as linear combinations of the columns of E */
172
/* write these in the rows of A */
173
zass_mat = tr_pose(tmp2);
174
free_mat(tmp2);
175
tmp = long_solve_mat(E,zass_mat);
176
if (tmp[1] != NULL){
177
fprintf(stderr,"error in basis_part\n");
178
exit(3);
179
}
180
A = tr_pose(tmp[0]);
181
free_mat(tmp[0]);
182
free(tmp);
183
free_mat(zass_mat);
184
185
/* make an gauss as far as possible and add indices */
186
old_rank = A->rows;
187
RES = init_mat(g->cols,E->cols-old_rank,"");
188
for (i=old_rank;i<E->cols;i++){
189
long_row_hnf(A);
190
real_mat(A,A->rows+1,A->cols);
191
192
/* search for a "step" */
193
for (j=0;j<A->rows && A->array.SZ[j][j]!=0;j++);
194
j--;
195
196
/* add one row vector of A and make sure the lattice stays pure */
197
if (j < 0){
198
A->array.SZ[A->rows-1][0] = 1;
199
}
200
else{
201
gcd_darstell(A->array.SZ[j][j],A->array.SZ[j][j+1],
202
A->array.SZ[A->rows-1]+j+1,A->array.SZ[A->rows-1]+j,&k);
203
A->array.SZ[A->rows-1][j+1] *= (-1);
204
}
205
206
/* stick this linear combination into RES */
207
for (j=0;j<A->cols;j++){
208
for (k=0;k<RES->rows;k++){
209
RES->array.SZ[k][i-old_rank] += A->array.SZ[A->rows-1][j]
210
* E->array.SZ[k][j];
211
}
212
}
213
}
214
215
/* cleanup */
216
free_mat(A);
217
free_mat(E);
218
219
return RES;
220
}
221
222
/******************************************************************************
223
@
224
@------------------------------------------------------------------------------
225
@
226
@ static matrix_TYP *normalize(matrix_TYP *g,int *dim,int flag)
227
@
228
@------------------------------------------------------------------------------
229
@
230
*******************************************************************************/
231
static matrix_TYP *normalize(matrix_TYP *g,int *dim,int flag)
232
{
233
234
matrix_TYP *h,
235
*RES,
236
**plse,
237
*tmp;
238
239
int i,
240
j,
241
k,
242
rank2;
243
244
/* set h = g - 1 */
245
h = copy_mat(g);
246
for (i=0;i<h->cols;i++)
247
h->array.SZ[i][i]--;
248
249
tmp = copy_mat(h);
250
modp_mat(tmp,2);
251
init_prime(2);
252
rank2 = p_gauss(tmp);
253
cleanup_prime();
254
255
plse = (matrix_TYP **) malloc(rank2 * sizeof(matrix_TYP *));
256
for (i=0;i<rank2;i++){
257
plse[i] = init_mat(h->rows,1,"");
258
k = 0;
259
for (j=0;j<tmp->cols && k==0;j++)
260
k = plse[i]->array.SZ[j][0] = tmp->array.SZ[i][j];
261
}
262
free_mat(tmp);
263
264
if (flag || rank2 == dim[0]){
265
dim[0] = rank2;
266
267
RES = init_mat(g->cols,g->cols,"");
268
269
for (i=0;i<rank2;i++){
270
for (j=0;j<g->cols;j++){
271
RES->array.SZ[j][2*i] = plse[i]->array.SZ[j][0];
272
}
273
tmp = mat_mul(g,plse[i]);
274
for (j=0;j<g->cols;j++){
275
RES->array.SZ[j][2*i+1] = tmp->array.SZ[j][0];
276
}
277
free_mat(tmp);
278
}
279
280
k = 2*rank2;
281
tmp = basis_part(g,h,plse,rank2,1);
282
for (i=0;i<tmp->cols;i++){
283
for (j=0;j<tmp->rows;j++){
284
RES->array.SZ[j][k] = tmp->array.SZ[j][i];
285
}
286
k++;
287
}
288
free_mat(tmp);
289
290
for (i=0;i<h->cols;i++)
291
h->array.SZ[i][i] += 2;
292
293
tmp = basis_part(g,h,plse,rank2,-1);
294
for (i=0;i<tmp->cols;i++){
295
for (j=0;j<tmp->rows;j++){
296
RES->array.SZ[j][k] = tmp->array.SZ[j][i];
297
}
298
k++;
299
}
300
free_mat(tmp);
301
}
302
else{
303
/* we didn't find an appropriate element */
304
RES = NULL;
305
}
306
307
/* free the memory */
308
for (i=0;i<rank2;i++)
309
free_mat(plse[i]);
310
if (plse != NULL) free(plse);
311
free_mat(h);
312
313
if (RES != NULL){
314
Check_mat(RES);
315
}
316
317
return RES;
318
}
319
320
/******************************************************************************
321
@
322
@------------------------------------------------------------------------------
323
@
324
@ bravais_TYP *catalog_number_v4(bravais_TYP *G,char *symb,
325
@ matrix_TYP **TR,int *almost,int *zclass)
326
@
327
@ Tests wheter the Bravais group G is isomorphic to C_2 or V_4.
328
@ In these cases it will return a group which is Z-equivalent to G
329
@ from the catalog which sits in TOPDIR/tables.
330
@
331
@ It will return a transfromation matrix via TR[0], and the position
332
@ in the catalog via almost[0] and zclass[0].
333
@
334
@ bravais_TYP *G : The group in question. Its order must be given.
335
@ char *symb : The symbol of the group. It can be calculated via symbol(..)
336
@ matrix_TYP **TR: pointer for the transformation matrix which transforms
337
@ the given group G to the group returned via konj_bravais,
338
@ ie. TR[0] * G * TR[0]^-1 = group returned.
339
@ int *almost : the position of the almost decomposable group in the
340
@ catalog is returned via this pointer.
341
@ int *zclass : 2 coordinate of the group in the catalog.
342
@
343
@------------------------------------------------------------------------------
344
@
345
*******************************************************************************/
346
bravais_TYP *catalog_number_v4(bravais_TYP *G,char *symb,
347
matrix_TYP **TR,int *almost,int *zclass)
348
{
349
350
bravais_TYP *T = NULL,
351
*H;
352
353
symbol_out *S;
354
355
matrix_TYP *X,
356
*g,
357
*g2,
358
*h,
359
*h2,
360
*TG,
361
*TG2;
362
363
char *file;
364
365
int i,
366
dim_g_F2;
367
368
if (G->dim > MAXDIM){
369
fprintf(stderr,"This program does only work up to dimension %d\n",
370
MAXDIM);
371
exit(3);
372
}
373
374
/* check whether we do have the trivial case of <-I_n> */
375
if ((strcmp(symb,"1") == 0) ||
376
(strcmp(symb,"1,1") == 0) ||
377
(strcmp(symb,"1,1,1") == 0) ||
378
(strcmp(symb,"1,1,1,1") == 0) ||
379
(strcmp(symb,"1,1,1,1,1") == 0) ||
380
(strcmp(symb,"1,1,1,1,1,1") == 0)){
381
almost[0] = 1;
382
zclass[0] = 1;
383
S = read_symbol_from_string(symb);
384
T = S->grp;
385
free(S);
386
free(S->fn);
387
TR[0] = init_mat(G->dim,G->dim,"1");
388
if (T->zentr_no > 0){
389
fprintf(stderr,"catalog_number: an error ocurred in the -I_n case\n");
390
exit(3);
391
}
392
return T;
393
}
394
395
/* firstly test whether we have a group isomorphic to v4 */
396
g = test_v4(G);
397
398
if (g!= NULL){
399
/* we got an element of G of order 2, which has non negative trace */
400
401
/* we should only have 1 almost decomposable family */
402
S = read_symbol_from_string(symb);
403
H = S->grp;
404
get_zentr(S);
405
if (S->fn != NULL){
406
fprintf(stderr,"catalog_number: an error occured in v4-part\n");
407
exit(3);
408
}
409
free(S);
410
411
/* throw away centralizer & normalizer, ist only hinders */
412
if (H->cen_no >0){
413
for (i=0;i<H->cen_no;i++) free_mat(H->cen[i]);
414
free(H->cen);
415
H->cen = NULL;
416
H->cen_no = 0;
417
}
418
if (H->normal_no >0){
419
for (i=0;i<H->normal_no;i++) free_mat(H->normal[i]);
420
free(H->normal);
421
H->normal = NULL;
422
H->normal_no = 0;
423
}
424
425
/* normalize g */
426
TG = normalize(g,&dim_g_F2,TRUE);
427
X = long_mat_inv(TG);
428
TG2 = mat_kon(X,g,TG);
429
free_mat(g);
430
free_mat(X);
431
g = TG2;
432
433
if (INFO_LEVEL & 4){
434
put_mat(TG,NULL,"TG",2);
435
put_mat(g,NULL,"g",2);
436
}
437
438
/* bare in mind that the trace is Q-invariant */
439
g2 = test_v4(H);
440
441
almost[0] = 1;
442
zclass[0] = -1;
443
TG2 = NULL;
444
while (TG2 ==0){
445
446
if (zclass[0] == (-1)){
447
h = copy_mat(g2);
448
}
449
else if (zclass[0] >= H->zentr_no){
450
fprintf(stderr,"bravais_catalog: v4-part: didn't find the group\n");
451
exit(3);
452
}
453
else{
454
X = mat_inv(H->zentr[zclass[0]]);
455
h = mat_kon(X,g2,H->zentr[zclass[0]]);
456
free_mat(X);
457
}
458
459
TG2 = normalize(h,&dim_g_F2,FALSE);
460
461
if (TG2 != NULL){
462
/* we found the corresponding group */
463
/* the transforming matrix is the quotient of TG and TG2 */
464
if (INFO_LEVEL & 4) put_mat(TG2,NULL,"TG2",2);
465
X = long_mat_inv(TG);
466
TR[0] = mat_mul(TG2,X);
467
if (zclass[0] < 0){
468
T = H;
469
H = NULL;
470
}
471
else{
472
T = Z_class(H,H->zentr[zclass[0]]);
473
}
474
}
475
476
free_mat(h);
477
478
zclass[0]++;
479
}
480
481
/* we started off with -1 */
482
zclass[0]++;
483
484
free_mat(g);
485
free_mat(g2);
486
free_mat(TG);
487
free_mat(TG2);
488
free_mat(X);
489
if (H != NULL) free_bravais(H);
490
491
}
492
493
return T;
494
}
495
496