Tensor Network Theory Library  Beta release 1.2.1
A library of routines for performing TNT-based operations
 All Data Structures Functions Variables Groups Pages
tntNodeUtil.c
1 /*
2 Authors: Sarah Al-Assam, Stephen Clark and Dieter Jaksch
3 $LastChangedDate: 2015-06-29 20:44:17 +0100 (Mon, 29 Jun 2015) $
4 (c) University of Oxford 2014
5 */
6 
15 /*-------------------------------------------*/
16 
17 #include "../headers/tnt_int.h"
18 #include "../headers/dec_public.h"
19 #include "../headers/dec_tnode.h"
20 #include "../headers/dec_network.h"
21 #include "../headers/dec_gen.h"
22 
23 
76 tntNode tntNodeCreateEyeLeg(tntNode A,
77  tntLegLabel legA,
78  tntNode B,
79  tntLegLabel legB)
80 {
81 
82  tntNode tnEye; /* The identity operator */
83  TNT_ERR_RET_DEFS /* return value from internal function */
84  tntIntArray dimsA, dirsA, qnsA; /* Dimensions and directions of the legs, quantum number information for the first leg of the identity node */
85  tntIntArray dimsB, dirsB, qnsB; /* Dimensions and directions of the legs, quantum number information for the second leg of the identity node */
86  unsigned lA, lB; /* Legs as integer values to use for the first leg */
87  unsigned lnumA, lnumB; /* Leg numbers that correspons to the ids passed */
88  unsigned *legids; /* leg ids for the new node */
89  int *legdims; /* leg dimensions for the new node */
90 
91  chk = legids = malloc(2*sizeof(unsigned)); TNT_PUB_MEM_CHK /* NO_COVERAGE */
92  chk = legdims = malloc(2*sizeof(int)); TNT_PUB_MEM_CHK /* NO_COVERAGE */
93 
94  ret = _tnt_tnode_checkqn(A);
95  TNT_PUB_ERR_CHK /* NO_COVERAGE */
96 
97  /* Convert characters to integers */
98  ret = _tnt_node_id_chartonum(&lA,legA[0]);
99  TNT_PUB_ERR_CHK /* NO_COVERAGE */
100 
101  /* Find lB */
102  if (legA[0] == legB[0]) {
103  if ('9' == legA[0]) ret = _tnt_node_id_chartonum(&lB,'0');
104  else if ('Z' == legA[0]) ret = _tnt_node_id_chartonum(&lB,'A');
105  else if ('z' == legA[0]) ret = _tnt_node_id_chartonum(&lB,'a');
106  else ret = _tnt_node_id_chartonum(&lB,legA[0]+1);
107  } else {
108  ret = _tnt_node_id_chartonum(&lB,legB[0]);
109  }
110  TNT_PUB_ERR_CHK /* NO_COVERAGE */
111 
112  /* get the dimensions of the first leg */
113  ret = _tnt_tnode_dimget(&dimsA, A);
114  TNT_PUB_ERR_CHK /* NO_COVERAGE */
115 
116  /* get the dimensions of the second leg */
117  ret = _tnt_tnode_dimget(&dimsB, B);
118  TNT_PUB_ERR_CHK /* NO_COVERAGE */
119 
120  ret = _tnt_tnode_findlegid(&lnumA, A, lA);
121  TNT_PUB_ERR_CHK /* NO_COVERAGE */
122 
123  ret = _tnt_tnode_findlegid(&lnumB, B, lB);
124  TNT_PUB_ERR_CHK /* NO_COVERAGE */
125 
126  /* set the leg id's and leg numbers of the node to create */
127  legids[0] = lA;
128  legids[1] = lB;
129  legdims[0] = dimsA.vals[lnumA];
130  legdims[1] = dimsB.vals[lnumB];
131 
132  /* create a node that has the same properties as the legs given but with identity elements */
133  ret = _tnt_tnode_create(&tnEye, EYE, VALS, NULL, 2, legids, legdims);
134  TNT_PUB_ERR_CHK /* NO_COVERAGE */
135 
136  tntIntArrayFree(&dimsA);
137  tntIntArrayFree(&dimsB);
138 
139  /* set qn info to match node */
140  /* get the direction of each leg - entries are given in order of legs */
141  ret = _tnt_tnode_dirget(&dirsA, A);
142  TNT_PUB_ERR_CHK /* NO_COVERAGE */
143  ret = _tnt_tnode_dirget(&dirsB, B);
144  TNT_PUB_ERR_CHK /* NO_COVERAGE */
145 
146  /* get the quantum number information for the legs of the supplied nodes, if it exists. */
147  /* Check whether there is qn info on the first leg */
148  if (0 != dirsA.vals[lnumA]) {
149  /* Get all the quantum numbers */
150  ret = _tnt_tnode_getqn(&qnsA, A, lA);
151  TNT_PUB_ERR_CHK /* NO_COVERAGE */
152 
153  /* Now set the qn info on this leg using the information */
154  ret = _tnt_tnode_setqn(tnEye, lA, qnsA.vals, dirsA.vals[lnumA]);
155  TNT_PUB_ERR_CHK /* NO_COVERAGE */
156 
157  /* Free array containing qn info for this leg */
158  tntIntArrayFree(&qnsA);
159  }
160  /* Repeat for the second leg */
161  if (0 != dirsB.vals[lnumB]) {
162  /* Get all the quantum numbers */
163  ret = _tnt_tnode_getqn(&qnsB, B, lB);
164  TNT_PUB_ERR_CHK /* NO_COVERAGE */
165 
166  /* Now set the qn info on this leg using the information */
167  ret = _tnt_tnode_setqn(tnEye, legids[1], qnsB.vals, dirsB.vals[lnumB]);
168  TNT_PUB_ERR_CHK /* NO_COVERAGE */
169 
170  /* Free array containing qn info for this leg */
171  tntIntArrayFree(&qnsB);
172  }
173 
174  /* free array containing leg directions */
175  tntIntArrayFree(&dirsA);
176  tntIntArrayFree(&dirsB);
177 
178 
179  /* return the identity node */
180  return tnEye;
181 }
182 
195 tntNode tntNodeCreateEyeOp(tntNode A)
196 {
197 
198  extern tntSystem systype; /* Internal decleration of global variable for system type */
199  tntNode tn_bs; /* Node to use as a basis for the for the identity */
200  tntNode tnEye; /* The identity operator */
201  TNT_ERR_RET_DEFS /* return value from internal function */
202  tntIntArray dims, dirs, qns, ids; /* Dimensions and directions of the legs, quantum number information for the identity node */
203  unsigned l, lnum; /* Used for looping through legs. Leg number of basis node that corresponds to this leg of tnEye */
204 
205  if (NULL == A) {
206  if (NULL == systype.basisOp) {
207  sprintf(tnt_err.errinfostr,"Cannot create identity operator using basis operator as the basis operator has not yet been set"); /* NO_COVERAGE */
208  sprintf(tnt_err.pubfuncname,__FUNCTION__); /* NO_COVERAGE */
209  _tnt_print_error(); /* NO_COVERAGE */
210  } else {
211  tn_bs = systype.basisOp;
212  }
213  } else {
214  tn_bs = A;
215 
216  ret = _tnt_tnode_checkqn(A);
217  TNT_PUB_ERR_CHK /* NO_COVERAGE */
218  }
219 
220 
221 
222  /* get the dimensions of the basis operator */
223  ret = _tnt_tnode_dimget(&dims, tn_bs);
224  TNT_PUB_ERR_CHK /* NO_COVERAGE */
225 
226  ret = _tnt_tnode_idget(&ids, tn_bs);
227  TNT_PUB_ERR_CHK /* NO_COVERAGE */
228 
229  /* create a node that has the same properties as the basis operator but with identity elements */
230  ret = _tnt_tnode_create(&tnEye, EYE, VALS, NULL, tn_bs->num_legs, (unsigned *) ids.vals, dims.vals);
231  TNT_PUB_ERR_CHK /* NO_COVERAGE */
232 
233  /* set qn info to match node */
234  if (tntSymmTypeGet()) {
235  /* get the direction of each leg - entries are given in order of legs */
236  ret = _tnt_tnode_dirget(&dirs, tn_bs);
237  TNT_PUB_ERR_CHK /* NO_COVERAGE */
238 
239  /* loop over all the legs numbers of the identity node */
240  for (l = 0; l < tnEye->num_legs; l++) {
241  /* get the quantum number information for this leg of the supplied operator, if it exists. */
242  /* Note we are being careful NOT to assume that the legs of tnEye are not in the same order as the legs of tn_bs */
243 
244  /* Get the leg number of tn_bs which corresponds to this leg */
245  ret = _tnt_tnode_findlegid(&lnum, tn_bs, tnEye->leg_id[l]);
246  TNT_PUB_ERR_CHK /* NO_COVERAGE */
247 
248  /* Check whether there is qn info on this leg */
249  if (0 != dirs.vals[lnum]) {
250  /* Get all the quantum numbers */
251  ret = _tnt_tnode_getqn(&qns, tn_bs, tnEye->leg_id[l]);
252  TNT_PUB_ERR_CHK /* NO_COVERAGE */
253 
254  /* Now set the qn info on this leg using the information */
255  ret = _tnt_tnode_setqn(tnEye, tnEye->leg_id[l], qns.vals, dirs.vals[lnum]);
256  TNT_PUB_ERR_CHK /* NO_COVERAGE */
257 
258  /* Free array containing qn info for this leg */
259  tntIntArrayFree(&qns);
260  }
261  }
262  /* free array containing leg directions */
263  tntIntArrayFree(&dirs);
264  }
265  /* return the identity node */
266  return tnEye;
267 }
268 
269 
270 
275 void tntNodeFree(tntNode *A)
276 {
277  TNT_ERR_RET_DEFS /* return value from internal function */
278 
279  ret = _tnt_tnode_free(A);
280  TNT_PUB_ERR_CHK /* NO_COVERAGE */
281 }
282 
283 
288 void tntNodeGroupFree(tntNode *A)
289 {
290  TNT_ERR_RET_DEFS /* return value from internal function */
291 
292  ret = _tnt_network_free(A);
293  TNT_PUB_ERR_CHK /* NO_COVERAGE */
294 }
295 
296 
297 #ifdef MAKINGPUBLICDOCS
298 /* Function calls function below through a C preprocessor macro */
304 tntNode tntNodeCopy(tntNode A)
305 {
306 }
307 #endif
308 
319 tntNode tntNodeCopyConj(tntNode A,
320  int conj)
321 {
322  struct tnode *tnc; /* The copy of the tnode */
323  TNT_ERR_RET_DEFS /* return value from internal function */
324 
325  ret = _tnt_tnode_checkqn(A);
326  TNT_PUB_ERR_CHK /* NO_COVERAGE */
327 
328  ret = _tnt_tnode_copy(&tnc, A, conj);
329  TNT_PUB_ERR_CHK /* NO_COVERAGE */
330 
331  return tnc;
332 
333 }
334 
335 
336 #ifdef MAKINGPUBLICDOCS
337 
353 /* Function call leads to function below through C pre-processor macro */
354 tntNode tntNodeCreate(tntComplexArray *nodeVals,
355  tntLegLabel leglabels,
356  unsigned dimleg1,
357  unsigned dim...)
358 #else
359 tntNode tntNodeCreateStatic(tntComplexArray *nodeVals,
360  tntLegLabel leglabels,
361  unsigned dimleg1,
362  unsigned dimleg2,
363  unsigned dimleg3,
364  unsigned dimleg4,
365  unsigned dimleg5,
366  unsigned dimleg6,
367  unsigned dimleg7,
368  unsigned dimleg8,
369  unsigned dimleg9,
370  unsigned dimleg10,
371  unsigned dimleg11,
372  unsigned dimleg12)
373 #endif
374 {
375  struct tnode *A; /* The new tnode */
376  union tensor_types elems; /* The elements of the tensor */
377  unsigned numLegs, *legId;
378  int *legdiml;
379  unsigned legDim[12] = {dimleg1,dimleg2,dimleg3,dimleg4,dimleg5,dimleg6,dimleg7,dimleg8,dimleg9,dimleg10,dimleg11,dimleg12};
380  unsigned loop;
381  unsigned tstsz=1; /* size calculated by multiplying the dimension of each leg */
382 
383  TNT_ERR_RET_DEFS /* return value from internal function */
384  char err_msg[TNT_STRLEN]; /* buffer for error messages */
385 
386  /* Convert string to array of numeric IDs */
387  ret = _tnt_node_id_strtonum(&numLegs, &legId, leglabels);
388  TNT_PUB_ERR_CHK /* NO_COVERAGE */
389 
390  /* First check that the size of the supplied array and the dimensions of the node are consistent */
391  for (loop=0; loop < numLegs; loop++) {
392  tstsz *= legDim[loop];
393  }
394 
395  if (nodeVals != NULL && tstsz != nodeVals->sz) {
396  sprintf(err_msg,"The product of the leg dimensions (%d) does not equal the size of the input array (%d)", tstsz, nodeVals->sz); /* NO_COVERAGE */
397  sprintf(tnt_err.errinfostr,"%s",err_msg); /* NO_COVERAGE */
398  sprintf(tnt_err.pubfuncname,"tntNodeCreate"); /* NO_COVERAGE */
399  _tnt_print_error(); /* NO_COVERAGE */
400  } /* NO_COVERAGE */
401 
402  /* Create an array for the leg dimensions and ids (to ensure memory allocated dynamically within library) */
403  chk = legdiml = malloc(numLegs*sizeof(int)); TNT_PUB_MEM_CHK /* NO_COVERAGE */
404 
405  for (loop=0; loop<numLegs; loop++) {
406  legdiml[loop] = (int) legDim[loop];
407  }
408 
409  if (nodeVals != NULL) {
410 
411  /* Create the structure to hold the tensor elements */
412  chk = elems.vals = malloc(sizeof(struct tnsr_values));
413  TNT_PUB_MEM_CHK /* NO_COVERAGE */
414 
415  /* Check whether there are any imaginary values (where values less that 1e-14 are taken to be zero) */
416  elems.vals->comp = 0;
417  for (loop=0; loop<nodeVals->sz; loop++) {
418  if (fabs(nodeVals->vals[loop].im) > TNT_DEFAULT_TOL) {
419  elems.vals->comp=1;
420  break;
421  }
422  }
423 
424  /* Allocate memory for the elements array and populate elements */
425  if (elems.vals->comp) {
426  chk = elems.vals->comarr = malloc(nodeVals->sz * sizeof(tntComplex));
427  TNT_PUB_MEM_CHK /* NO_COVERAGE */
428 
429  for (loop = 0; loop< nodeVals->sz; loop++) elems.vals->comarr[loop] = nodeVals->vals[loop];
430 
431  } else {
432  chk = elems.vals->rearr = malloc(nodeVals->sz * sizeof(double));
433  TNT_PUB_MEM_CHK /* NO_COVERAGE */
434 
435  for (loop = 0; loop< nodeVals->sz; loop++) elems.vals->rearr[loop] = nodeVals->vals[loop].re;
436  }
437  elems.vals->sz = nodeVals->sz;
438 
439  /* Check the that the number of rows and columns in the input array matches the dimensions */
440  if (1 == numLegs){
441  /* If there is only one leg, only one of rowsize or colzise can be not 1: default to column vector */
442  if (nodeVals->numrows > 1 && nodeVals->numcols > 1) {
443  elems.vals->rowsize = 1;
444  elems.vals->colsize = nodeVals->sz;
445  } else {
446  elems.vals->rowsize = nodeVals->numrows;
447  elems.vals->colsize = nodeVals->numcols;
448  }
449  } else {
450  tstsz = legDim[0];
451  if (nodeVals->numrows > 1 && nodeVals->numcols > 1) {
452  for (loop = 1; loop < numLegs; loop++) {
453  if (tstsz >= nodeVals->numrows) break;
454  tstsz *= legDim[loop];
455  }
456  }
457  elems.vals->rowsize = tstsz;
458  elems.vals->colsize = nodeVals->sz/tstsz;
459  }
460 
461  ret = _tnt_tnode_create(&A, PRELOAD, VALS, &elems, numLegs, legId, legdiml);
462  TNT_PUB_ERR_CHK /* NO_COVERAGE */
463 
464  } else { /* Creating a random node */
465 
466 
467  ret = _tnt_tnode_create(&A, RANDOM, VALS, &elems, numLegs, legId,legdiml);
468  TNT_PUB_ERR_CHK /* NO_COVERAGE */
469  }
470 
471  return A;
472 
473 }
474 
475 
476 #ifdef MAKINGPUBLICDOCS
477 
494 /* Function call leads to function below through C pre-processor macro */
495 tntNode tntNodeFuncCreate(tntComplexArray *nodeVals,
496  unsigned numops, char *opstr,
497  tntLegLabel leglabels,
498  unsigned dimleg1,
499  unsigned dim...)
500 #else
501 tntNode tntNodeFuncCreateStatic(tntComplexArray *nodeVals,
502  unsigned numops,
503  char *opstr,
504  tntLegLabel leglabels,
505  unsigned dimleg1,
506  unsigned dimleg2,
507  unsigned dimleg3,
508  unsigned dimleg4,
509  unsigned dimleg5,
510  unsigned dimleg6,
511  unsigned dimleg7,
512  unsigned dimleg8,
513  unsigned dimleg9,
514  unsigned dimleg10,
515  unsigned dimleg11,
516  unsigned dimleg12)
517 #endif
518 {
519  struct tnode *A; /* The new tnode */
520  union tensor_types elems; /* The elements of the tensor */
521  unsigned numLegs, *legId;
522  int *legdiml;
523  unsigned k;
524  unsigned legDim[12] = {dimleg1,dimleg2,dimleg3,dimleg4,dimleg5,dimleg6,dimleg7,dimleg8,dimleg9,dimleg10,dimleg11,dimleg12};
525  unsigned loop;
526  unsigned tstsz=1; /* size calculated by multiplying the dimension of each leg */
527 
528  TNT_ERR_RET_DEFS /* return value from internal function */
529  char err_msg[TNT_STRLEN]; /* buffer for error messages */
530 
531  /* Convert string to array of numeric IDs */
532  ret = _tnt_node_id_strtonum(&numLegs, &legId, leglabels);
533  TNT_PUB_ERR_CHK /* NO_COVERAGE */
534 
535  /* First check that the size of the supplied array and the dimensions of the node are consistent */
536  for (loop=0; loop < numLegs; loop++) {
537  tstsz *= legDim[loop];
538  }
539 
540  if (tstsz != nodeVals[0].sz) {
541  sprintf(err_msg,"The product of the leg dimensions (%d) does not equal the size of the input array (%d)", tstsz, nodeVals->sz); /* NO_COVERAGE */
542  sprintf(tnt_err.errinfostr,"%s",err_msg); /* NO_COVERAGE */
543  sprintf(tnt_err.pubfuncname,"tntNodeFuncCreate"); /* NO_COVERAGE */
544  _tnt_print_error(); /* NO_COVERAGE */
545  } /* NO_COVERAGE */
546 
547  for (k = 1; k < numops; k++) {
548  if (nodeVals[1].sz != nodeVals[0].sz) {
549  sprintf(err_msg,"All operators must have the same number of elements"); /* NO_COVERAGE */
550  sprintf(tnt_err.errinfostr,"%s",err_msg); /* NO_COVERAGE */
551  sprintf(tnt_err.pubfuncname,"tntNodeFuncCreate"); /* NO_COVERAGE */
552  _tnt_print_error(); /* NO_COVERAGE */
553  }
554  }
555 
556  /* Create an array for the leg dimensions and ids (to ensure memory allocated dynamically within library) */
557  chk = legdiml = malloc(numLegs*sizeof(int));
558  TNT_PUB_MEM_CHK /* NO_COVERAGE */
559 
560  for (loop=0; loop<numLegs; loop++) {
561  legdiml[loop] = (int) legDim[loop];
562  }
563 
564  /* Create the structure to hold the tensor elements */
565  chk = elems.params = malloc(sizeof(struct tnsr_params));
566  TNT_PUB_MEM_CHK /* NO_COVERAGE */
567 
568  elems.params->num_op = numops;
569 
570  /* Create the structure to hold the tensor elements */
571  chk = elems.params->op = malloc(numops * sizeof(struct tnsr_values));
572  TNT_PUB_MEM_CHK /* NO_COVERAGE */
573 
574  /* Check whether there are any imaginary values (where values less that 1e-14 are taken to be zero) */
575  for (k = 0; k < numops; k++) {
576  elems.params->comp=0;
577  for (loop = 0; loop < nodeVals->sz; loop++) {
578  if (fabs(nodeVals[k].vals[loop].im) > TNT_DEFAULT_TOL) {
579  elems.params->comp=1;
580  break;
581  }
582  }
583  }
584 
585  /* Check the that the number of rows and columns in the input array matches the dimensions */
586  if (1 == numLegs){
587  /* If there is only one leg, only one of rowsize or colzise can be not 1: default to column vector */
588  if (nodeVals->numrows > 1 && nodeVals->numcols > 1) {
589  elems.params->rowsize = 1;
590  elems.params->colsize = nodeVals->sz;
591  } else {
592  elems.params->rowsize = nodeVals->numrows;
593  elems.params->colsize = nodeVals->numcols;
594  }
595  } else {
596  tstsz = legDim[0];
597  if (nodeVals->numrows > 1 && nodeVals->numcols > 1) {
598  for (loop = 1; loop < numLegs; loop++) {
599  if (tstsz >= nodeVals->numrows) break;
600  tstsz *= legDim[loop];
601  }
602  }
603  elems.params->rowsize = tstsz;
604  elems.params->colsize = nodeVals->sz/tstsz;
605  }
606 
607  /* Get the function type */
608  if (0 == strcmp("sum", opstr)) elems.params->gen_func = gen_sum;
609  else if (0 == strcmp("exp", opstr)) elems.params->gen_func = gen_exp;
610  else elems.params->gen_func = gen_sum;
611 
612  for (k = 0; k < numops; k++) {
613  /* Allocate memory for the elements array and populate elements */
614  if (elems.params->comp) {
615  elems.params->op[k].comp = 1;
616 
617  chk = elems.params->op[k].comarr = malloc(nodeVals->sz * sizeof(tntComplex));
618  TNT_PUB_MEM_CHK /* NO_COVERAGE */
619 
620  for (loop = 0; loop < nodeVals->sz; loop++) elems.params->op[k].comarr[loop] = nodeVals[k].vals[loop];
621 
622  } else {
623  elems.params->op[k].comp = 0;
624 
625  chk = elems.params->op[k].rearr = malloc(nodeVals->sz * sizeof(double));
626  TNT_PUB_MEM_CHK /* NO_COVERAGE */
627 
628  for (loop = 0; loop< nodeVals->sz; loop++) elems.params->op[k].rearr[loop] = nodeVals[k].vals[loop].re;
629  }
630 
631  elems.params->op[k].sz = nodeVals->sz;
632  elems.params->op[k].rowsize = elems.params->rowsize;
633  elems.params->op[k].colsize = elems.params->colsize;
634 
635 
636  ret = _tnt_tnode_create(&A, PRELOAD, PRMS, &elems, numLegs, legId, legdiml);
637  TNT_PUB_ERR_CHK /* NO_COVERAGE */
638 
639  }
640 
641  return A;
642 
643 }
644 
651 void tntNodeSetRealParam(tntNode A,
652  double pval,
653  unsigned pnum)
654 {
655  TNT_ERR_RET_DEFS /* return value from internal function */
656 
657  ret = _tnt_tnode_setrealparam(A, pval, pnum);
658  TNT_PUB_ERR_CHK/* NO_COVERAGE */
659 }
660 
661 
668 void tntNodeSetCompParam(tntNode A,
669  tntComplex pval,
670  unsigned pnum)
671 {
672  TNT_ERR_RET_DEFS /* return value from internal function */
673 
674  ret = _tnt_tnode_setcompparam(A, pval, pnum);
675  TNT_PUB_ERR_CHK /* NO_COVERAGE */
676 }
677 
tntNode tntNodeCopy(tntNode A)
Definition: tntNodeUtil.c:304
void tntNodeGroupFree(tntNode *A)
Definition: tntNodeUtil.c:288
tntSystem systype
Definition: tntSys.c:12
tntNode tntNodeFuncCreate(tntComplexArray *nodeVals, unsigned numops, char *opstr, tntLegLabel leglabels, unsigned dimleg1, unsigned dim...)
Definition: tntNodeUtil.c:495
tntNode tntNodeCreateEyeOp(tntNode A)
Definition: tntNodeUtil.c:195
tntNode tntNodeCreateEyeLeg(tntNode A, tntLegLabel legA, tntNode B, tntLegLabel legB)
Definition: tntNodeUtil.c:76
void tntNodeSetCompParam(tntNode A, tntComplex pval, unsigned pnum)
Definition: tntNodeUtil.c:668
void tntNodeFree(tntNode *A)
Definition: tntNodeUtil.c:275
Definition: tnt.h:65
void tntIntArrayFree(tntIntArray *arr)
Definition: tntArray.c:620
tntNode tntNodeCopyConj(tntNode A, int conj)
Definition: tntNodeUtil.c:319
void tntNodeSetRealParam(tntNode A, double pval, unsigned pnum)
Definition: tntNodeUtil.c:651
tntNode tntNodeCreate(tntComplexArray *nodeVals, tntLegLabel leglabels, unsigned dimleg1, unsigned dim...)
Definition: tntNodeUtil.c:354
int tntSymmTypeGet(void)
Definition: tntSys.c:498