Trisurf Monte Carlo simulator
Samo Penic
2015-10-06 b452d7494b80d355809bea9cefb53a8b8a15202d
commit | author | age
d7639a 1 #include<stdlib.h>
SP 2 #include<math.h>
3 #include<string.h>
4 #include "general.h"
5 #include "vertex.h"
a10dd5 6 #include "bond.h"
d7639a 7 #include<stdio.h>
SP 8
ea1cce 9 ts_bool vertex_list_assign_id(ts_vertex_list *vlist, ts_uint id){
M 10     ts_uint i;    
11     for(i=0;i<vlist->n;i++){
12         vlist->vtx[i]->id = id;
13     }
14     return TS_SUCCESS;
15 }
16
73f967 17 ts_vertex_list *init_vertex_list(ts_uint N){    
d7639a 18     ts_int i;
a10dd5 19     ts_vertex_list *vlist=(ts_vertex_list *)malloc(sizeof(ts_vertex_list));
73f967 20     
d7639a 21     if(N==0){
SP 22         err("Initialized vertex list with zero elements. Pointer set to NULL");
73f967 23         vlist->n=0;
SP 24         vlist->vtx=NULL;
25         return vlist;
d7639a 26     }
73f967 27     
8f6a69 28     vlist->vtx=(ts_vertex **)calloc(N,sizeof(ts_vertex *));
SP 29     if(vlist->vtx==NULL)
73f967 30         fatal("Fatal error reserving memory space for vertex list! Could number of requsted vertices be too large?", 100);
a10dd5 31     for(i=0;i<N;i++) {
8f6a69 32         vlist->vtx[i]=(ts_vertex *)calloc(1,sizeof(ts_vertex));
a10dd5 33         vlist->vtx[i]->idx=i;
074a17 34
SP 35     /* initialize Ylm for spherical hamonics DONE in sh.c */
36 /*    for(i=0;i<l;i++){
37         vlist->vtx[i]->Ylm[i]=(ts_double **)calloc(2*i+1,sizeof(ts_double *));
38         for(j=0;j<(2*i+1);j++){
39             clist->vtx[i]->Ylm[i][j]=(ts_double *)calloc(sizeof(ts_double));
40         }
41     }
42 */
43
44
a10dd5 45     }
73f967 46     vlist->n=N;
d7639a 47     return vlist;
SP 48 }
49
737714 50 ts_bool vtx_add_neighbour(ts_vertex *vtx, ts_vertex *nvtx){
d7639a 51     ts_uint i;
SP 52     /* no neighbour can be null! */
53     if(vtx==NULL || nvtx==NULL) return TS_FAIL;
54     
55     /*if it is already a neighbour don't add it to the list */
8f6a69 56     for(i=0; i<vtx->neigh_no;i++){
SP 57         if(vtx->neigh[i]==nvtx) return TS_FAIL;
d7639a 58     }
8f6a69 59     ts_uint nn=++vtx->neigh_no;
SP 60     vtx->neigh=(ts_vertex **)realloc(vtx->neigh, nn*sizeof(ts_vertex *));
61     vtx->neigh[nn-1]=nvtx;
3131dc 62 /* This was a bug in creating DIPYRAMID (the neighbours were not in right
SP 63  * order).
64  */
d7639a 65     /* pa se sosedu dodamo vertex */
SP 66     /*if it is already a neighbour don't add it to the list */
3131dc 67 /*
737714 68     for(i=0; i<nvtx->data->neigh_no;i++){
SP 69         if(nvtx->data->neigh[i]==vtx) return TS_FAIL;
d7639a 70     } 
a10dd5 71     nn=++nvtx->data->neigh_no;
737714 72     nvtx->data->neigh=(ts_vertex **)realloc(nvtx->data->neigh, nn*sizeof(ts_vertex *));
a10dd5 73     nvtx->data->neigh[nn-1]=vtx;
3131dc 74 */
d7639a 75
SP 76     return TS_SUCCESS;
77 }
a10dd5 78
9802f1 79 /* TODO: optimize this. test this. */
SP 80 ts_bool vtx_remove_neighbour(ts_vertex *vtx, ts_vertex *nvtx){
81 /* find a neighbour */
82 /* remove it from the list while shifting remaining neighbours up */
e19e79 83     ts_uint i,j=0;
8f6a69 84     for(i=0;i<vtx->neigh_no;i++){
e19e79 85 //        fprintf(stderr,"neigh_addr=%ld\n", (long)vtx->neigh[i]);
8f6a69 86         if(vtx->neigh[i]!=nvtx){
SP 87             vtx->neigh[j]=vtx->neigh[i];
9802f1 88             j++;
SP 89         }
90     }
e19e79 91 //    fprintf(stderr,"remove_neighbour: vtx1_addr=%ld, vtx2_addr=%ld\n",(long)vtx,(long)nvtx);
9802f1 92 /* resize memory. potentionally time consuming */
8f6a69 93     vtx->neigh_no--;
SP 94     vtx->neigh=(ts_vertex **)realloc(vtx->neigh,vtx->neigh_no*sizeof(ts_vertex *));
95     if(vtx->neigh == NULL && vtx->neigh_no!=0)
e19e79 96         fatal("(1) Reallocation of memory failed during removal of vertex neighbour in vtx_remove_neighbour",100);
SP 97 //fprintf(stderr,"first alloc");
9802f1 98 /* repeat for the neighbour */
SP 99 /* find a neighbour */
100 /* remove it from the list while shifting remaining neighbours up */
e19e79 101     j=0;
8f6a69 102     for(i=0;i<nvtx->neigh_no;i++){
SP 103         if(nvtx->neigh[i]!=vtx){
104             nvtx->neigh[j]=nvtx->neigh[i];
9802f1 105             j++;
SP 106         }
107     }
108 /* resize memory. potentionally time consuming. */
e19e79 109 //    fprintf(stderr,"Neigbours=%d\n",nvtx->neigh_no);
8f6a69 110     nvtx->neigh_no--;
e19e79 111             nvtx->neigh=(ts_vertex **)realloc(nvtx->neigh,nvtx->neigh_no*sizeof(ts_vertex *));
SP 112 //    fprintf(stderr,"Neigbours=%d\n",nvtx->neigh_no);
8f6a69 113     if(nvtx->neigh == NULL && nvtx->neigh_no!=0)
e19e79 114         fatal("(2) Reallocation of memory failed during removal of vertex neighbour in vtx_remove_neighbour",100);
9802f1 115
SP 116     return TS_SUCCESS;
117 }
7958e9 118
9802f1 119
SP 120
a10dd5 121 ts_bool vtx_add_bond(ts_bond_list *blist,ts_vertex *vtx1,ts_vertex *vtx2){
SP 122     ts_bond *bond;
123     bond=bond_add(blist,vtx1,vtx2);
124     if(bond==NULL) return TS_FAIL;
8f6a69 125     vtx1->bond_no++;
30ee9c 126     vtx2->bond_no++;
3131dc 127    // vtx2->data->bond_no++;
a10dd5 128
8f6a69 129     vtx1->bond=(ts_bond **)realloc(vtx1->bond, vtx1->bond_no*sizeof(ts_bond *)); 
30ee9c 130     vtx2->bond=(ts_bond **)realloc(vtx2->bond, vtx2->bond_no*sizeof(ts_bond *)); 
3131dc 131    // vtx2->data->bond=(ts_bond **)realloc(vtx2->data->bond, vtx2->data->bond_no*sizeof(ts_bond *)); 
8f6a69 132     vtx1->bond[vtx1->bond_no-1]=bond;
30ee9c 133     vtx2->bond[vtx2->bond_no-1]=bond;
8f6a69 134    // vtx2->ata->bond[vtx2->data->bond_no-1]=bond;
a10dd5 135     return TS_SUCCESS;
SP 136 }
137
138 ts_bool vtx_add_cneighbour(ts_bond_list *blist, ts_vertex *vtx1, ts_vertex *vtx2){
139     ts_bool retval;
140     retval=vtx_add_neighbour(vtx1,vtx2);
e19e79 141   //  retval=vtx_add_neighbour(vtx2,vtx1);
a10dd5 142     if(retval==TS_SUCCESS)
SP 143     retval=vtx_add_bond(blist,vtx1,vtx2); 
144     return retval;
145 }
146
9802f1 147 /*TODO: write and optimize this urgently before use! */
SP 148 ts_bool vtx_remove_cneighbour(ts_bond_list *blist, ts_vertex *vtx1, ts_vertex
149 *vtx2){
150 //    ts_bool retval;
151 /* remove the bond */
152 //retval=vtx_remove_bond(blist,vtx1,vtx2);
153 /* remove the vertices */
154     return TS_SUCCESS;
155 }
a10dd5 156
d7639a 157
737714 158 ts_bool vtx_free(ts_vertex  *vtx){
8f6a69 159     if(vtx->neigh!=NULL)   free(vtx->neigh);
SP 160     if(vtx->tristar!=NULL) free(vtx->tristar);
161     if(vtx->bond!=NULL)    free(vtx->bond);
737714 162     free(vtx);
d7639a 163     return TS_SUCCESS;
SP 164 }
165
73f967 166 ts_bool vtx_list_free(ts_vertex_list *vlist){
SP 167     int i;
168     for(i=0;i<vlist->n;i++){
8f6a69 169         if(vlist->vtx[i]!=NULL) vtx_free(vlist->vtx[i]);
73f967 170     }
8f6a69 171     //free(*(vlist->vtx));
737714 172     free(vlist->vtx);
73f967 173     free(vlist);
SP 174     return TS_SUCCESS;
175 }
d7639a 176
bb77ca 177 inline ts_double vtx_distance_sq(ts_vertex *vtx1, ts_vertex *vtx2){
d7639a 178     ts_double dist;
SP 179 #ifdef TS_DOUBLE_DOUBLE
8f6a69 180     dist=pow(vtx1->x-vtx2->x,2) + pow(vtx1->y-vtx2->y,2) + pow(vtx1->z-vtx2->z,2);
d7639a 181 #endif
SP 182 #ifdef TS_DOUBLE_LONGDOUBLE
8f6a69 183     dist=powl(vtx1->x-vtx2->x,2) + powl(vtx1->y-vtx2->y,2) + powl(vtx1->z-vtx2->z,2);
d7639a 184 #endif
SP 185 #ifdef TS_DOUBLE_FLOAT
8f6a69 186     dist=powf(vtx1->x-vtx2->x,2) + powf(vtx1->y-vtx2->y,2) + powf(vtx1->z-vtx2->z,2);
d7639a 187 #endif
SP 188     return(dist);
189 }
bb77ca 190
7958e9 191
SP 192
193 ts_bool vtx_set_global_values(ts_vesicle *vesicle){ 
194     ts_double xk=vesicle->bending_rigidity;
195     ts_uint i; 
196     for(i=0;i<vesicle->vlist->n;i++){
8f6a69 197         vesicle->vlist->vtx[i]->xk=xk;
7958e9 198     }
SP 199     return TS_SUCCESS;
200 }
201
063f2e 202 /** Calculates the triple product of vectors defined by vertices vtx1, vtx2 and vtx3, ($\mathrm{vtx}_1\cdot(\mathrm{vtx}_2\cross\mathrm{vtx}_3$):
SP 203  *  \begin{vmatrix}
204  *  x_1 & y_1 & z_1 \\
205  *  x_2-x_1 & y_2-y_1 & z_2-z_1\\
206  *  x_3-x_1 & y_3-y_1 & z_3-z_1\\
207  *  \end{vmatrix}
208  *  where the vertices coordinates are denoted by corresponding vertex index number. Function is used to determine the orientation of area formed by triangle formed by the three given vertices.
209  *
210  *      @param vtx1 is first vertex, according to which the orientation is calculated
211  *      @param vtx2 is the second vertex
212  *      @param vtx3 is the third vertex
213  *      @returns directionality of the area of the triangle formed by vertices vtx1, vtx2 and vtx3. It is positive if vtx1, vtx2 and vtx3 are oriented counter-clockwise.
214 */
7958e9 215 inline ts_double vtx_direct(ts_vertex *vtx1, ts_vertex *vtx2, ts_vertex *vtx3){
8f6a69 216     ts_double dX2=vtx2->x-vtx1->x;
SP 217     ts_double dY2=vtx2->y-vtx1->y;
218     ts_double dZ2=vtx2->z-vtx1->z;
219     ts_double dX3=vtx3->x-vtx1->x;
220     ts_double dY3=vtx3->y-vtx1->y;
221     ts_double dZ3=vtx3->z-vtx1->z;
222     ts_double direct=vtx1->x*(dY2*dZ3 -dZ2*dY3)+ 
223         vtx1->y*(dZ2*dX3-dX2*dZ3)+
224         vtx1->z*(dX2*dY3-dY2*dX3);
7958e9 225     return(direct);    
SP 226 }
227
228
229 inline ts_bool vertex_add_tristar(ts_vertex *vtx, ts_triangle *tristarmem){
8f6a69 230     vtx->tristar_no++;
SP 231     vtx->tristar=(ts_triangle **)realloc(vtx->tristar,vtx->tristar_no*sizeof(ts_triangle *));
232     if(vtx->tristar==NULL){
7958e9 233             fatal("Reallocation of memory while adding tristar failed.",3);
SP 234     }
8f6a69 235     vtx->tristar[vtx->tristar_no-1]=tristarmem;
7958e9 236     return TS_SUCCESS;
SP 237 }
238
f74313 239
30ee9c 240 /* Insert neighbour is a function that is required in bondflip. It inserts a
SP 241  * neighbour exactly in the right place. */
242 inline ts_bool vtx_insert_neighbour(ts_vertex *vtx, ts_vertex *nvtx, ts_vertex *vtxm){
243 //nvtx is a vertex that is to be inserted after vtxm!
244         ts_uint i,j,midx;
245         vtx->neigh_no++;
246         if(vtxm==NULL ||  nvtx==NULL || vtx==NULL)
247                 fatal("vertex_insert_neighbour: one of pointers has been zero.. Cannot proceed.",3);
248         //We need to reallocate space! The pointer *neight must be zero if not having neighbours jey (if neigh_no was 0 at thime of calling
249         vtx->neigh=realloc(vtx->neigh,vtx->neigh_no*sizeof(ts_vertex *));
250         if(vtx->neigh == NULL){
251             fatal("Reallocation of memory failed during insertion of vertex neighbour in vertex_insert_neighbour",3);
252         }
253         midx=0;
254         for(i=0;i<vtx->neigh_no-1;i++) if(vtx->neigh[i]==vtxm) {midx=i; break;}
255      //   fprintf(stderr,"midx=%d, vseh=%d\n",midx,vtx->neigh_no-2);
256         if(midx==vtx->neigh_no-2) {
257             vtx->neigh[vtx->neigh_no-1]=nvtx;
258         } else {
259             for(j=vtx->neigh_no-2;j>midx;j--) {
260                 vtx->neigh[j+1]=vtx->neigh[j];
261 //                vtx->bond_length[j+1]=vtx->bond_length[j];
262 //                vtx->bond_length_dual[j+1]=vtx->bond_length_dual[j];
263             }
264             vtx->neigh[midx+1]=nvtx;
265         }
266     return TS_SUCCESS;
267 }
268
269
270 /* vtx remove tristar is required in  bondflip. */
271 /* TODO: Check whether it is important to keep the numbering of tristar
272  * elements in some order or not! */
273 inline ts_bool vtx_remove_tristar(ts_vertex *vtx, ts_triangle *tristar){
274     ts_uint i,j=0;
275     for(i=0;i<vtx->tristar_no;i++){
276         if(vtx->tristar[i]!=tristar){
277             vtx->tristar[j]=vtx->tristar[i];
278             j++;
279         }
280     }
281     vtx->tristar_no--;
282     vtx->tristar=realloc(vtx->tristar,vtx->tristar_no*sizeof(ts_triangle *));
283     if(vtx->neigh == NULL){
284             fatal("Reallocation of memory failed during insertion of vertex neighbour in vertex_add_neighbour",3);
285         }
286     return TS_SUCCESS;
287 }
288
289
290
f74313 291 /* ****************************************************************** */
SP 292 /* ***** New vertex copy operations. Inherently they are slow.  ***** */
293 /* ****************************************************************** */
294
b01cc1 295 ts_bool vtx_copy(ts_vertex *cvtx, ts_vertex *ovtx){
f74313 296     memcpy((void *)cvtx,(void *)ovtx,sizeof(ts_vertex));
8f6a69 297     cvtx->neigh=NULL;
SP 298     cvtx->neigh_no=0;
299     cvtx->tristar_no=0;
300     cvtx->bond_no=0;
301     cvtx->tristar=NULL;
302     cvtx->bond=NULL;
303     cvtx->cell=NULL;
b01cc1 304     return TS_SUCCESS;
f74313 305 }
dac2e5 306
SP 307 ts_bool vtx_duplicate(ts_vertex *cvtx, ts_vertex *ovtx){
308     memcpy((void *)cvtx,(void *)ovtx,sizeof(ts_vertex));
309     return TS_SUCCESS;
310 }
311
f74313 312 //TODO: needs to be done
SP 313 ts_vertex **vtx_neigh_copy(ts_vertex_list *vlist,ts_vertex *ovtx){
314         return NULL;
315 }
316
dac2e5 317
SP 318
f74313 319 ts_vertex_list *vertex_list_copy(ts_vertex_list *ovlist){
SP 320     ts_uint i;
321     ts_vertex_list *vlist=(ts_vertex_list *)malloc(sizeof(ts_vertex_list));
b01cc1 322     vlist=memcpy((void *)vlist, (void *)ovlist, sizeof(ts_vertex_list));
f74313 323     ts_vertex **vtx=(ts_vertex **)malloc(vlist->n*sizeof(ts_vertex *));
b01cc1 324     vlist->vtx=vtx;
8f6a69 325     if(vlist->vtx==NULL)
b01cc1 326         fatal("Fatal error reserving memory space for vertex list! Could number of requsted vertices be too large?", 100);
SP 327     for(i=0;i<vlist->n;i++) {
8f6a69 328         vlist->vtx[i]=(ts_vertex *)calloc(1,sizeof(ts_vertex));
b01cc1 329         vlist->vtx[i]->idx=i;
SP 330         vtx_copy(vlist->vtx[i],ovlist->vtx[i]);
f74313 331     }
b01cc1 332
f74313 333     return vlist;
SP 334 }