Doxygen Source Code Documentation
SUMA_SurfClust.c File Reference
#include "SUMA_suma.h"
Go to the source code of this file.
Defines | |
#define | SUMA_ADD_NODE_TO_CLUST(dothisnode, Clust, NodeArea, ToBeAssigned) |
Enumerations | |
enum | SUMA_CLUST_BUILD_METHODS { SUMA_NO_BUILD_METHOD, SUMA_OFFSETS2, SUMA_OFFSETS_LL, SUMA_OFFSETS2_NO_REC } |
Functions | |
void | SUMA_FreeClustDatum (void *data) |
float * | SUMA_CalculateNodeAreas (SUMA_SurfaceObject *SO) |
Calculate area of each node as one third of the sum of the areas of incident triangles. If you change this function make sure changes are also done on RickR's compute_node_areas since the two functions use the same principle. | |
SUMA_CLUST_DATUM * | SUMA_Build_Cluster_From_Node (int dothisnode, SUMA_CLUST_DATUM *AddToThisClust, float *ToBeAssigned, int *N_TobeAssigned, float *NodeArea, SUMA_SurfaceObject *SO, SUMA_SURFCLUST_OPTIONS *Opt) |
builds a cluster starting from some node | |
SUMA_CLUST_DATUM * | SUMA_Build_Cluster_From_Node_NoRec (int dothisnode, float *ToBeAssigned, int *N_TobeAssigned, float *NodeArea, SUMA_SurfaceObject *SO, SUMA_SURFCLUST_OPTIONS *Opt) |
builds a cluster starting from some node | |
DList * | SUMA_FindClusters (SUMA_SurfaceObject *SO, int *ni, float *nv, int N_ni, int dothisnode, SUMA_SURFCLUST_OPTIONS *Opt, float *NodeArea) |
Finds clusters of data on the surface. | |
SUMA_Boolean | SUMA_Show_SurfClust_list (DList *list, FILE *Out, int detail, char *params) |
char * | SUMA_Show_SurfClust_list_Info (DList *list, int detail, char *params) |
SUMA_DSET * | SUMA_MaskDsetByClustList (SUMA_DSET *idset, SUMA_SurfaceObject *SO, DList *list, SUMA_Boolean FullList, char *leName) |
SUMA_DSET * | SUMA_SurfClust_list_2_DsetMask (SUMA_SurfaceObject *SO, DList *list, SUMA_Boolean FullList, char *leName) |
int | SUMA_ClusterCenterofMass (SUMA_SurfaceObject *SO, SUMA_CLUST_DATUM *cd, int UseSurfDist) |
Finds a node that best approximates the property of the center of mass on the surface. Note that the real center of mass of a curved surface is rarely on the surface, so this is an attempt at localizing a node that is central to an ROI and that can reflect the weight, or activity, distribution in that ROI. | |
SUMA_Boolean | SUMA_Sort_ClustersList (DList *list, SUMA_SURF_CLUST_SORT_MODES SortMode) |
Variables | |
SUMA_CommonFields * | SUMAg_CF |
SUMA_DO * | SUMAg_DOv |
SUMA_SurfaceViewer * | SUMAg_SVv |
int | SUMAg_N_SVv |
int | SUMAg_N_DOv |
int | BuildMethod |
Define Documentation
|
Value: { \ if (LocalHead) fprintf(SUMA_STDERR,"%s: Adding node %d to cluster %p of %d nodes\n", FuncName, dothisnode, Clust, Clust->N_Node); \ Clust->NodeList[Clust->N_Node] = dothisnode; \ Clust->totalarea += NodeArea[dothisnode]; \ Clust->totalvalue += ToBeAssigned[dothisnode]; \ Clust->totalabsvalue += (float)fabs((float)ToBeAssigned[dothisnode]); \ if (ToBeAssigned[dothisnode] < Clust->minvalue) { Clust->minvalue = ToBeAssigned[dothisnode]; Clust->minnode = dothisnode; } \ if (ToBeAssigned[dothisnode] > Clust->maxvalue) { Clust->maxvalue = ToBeAssigned[dothisnode]; Clust->maxnode = dothisnode; } \ Clust->ValueList[Clust->N_Node] = ToBeAssigned[dothisnode]; \ ++Clust->N_Node; \ } Definition at line 246 of file SUMA_SurfClust.c. Referenced by SUMA_Build_Cluster_From_Node_NoRec(). |
Enumeration Type Documentation
|
Definition at line 27 of file SUMA_SurfClust.c.
|
Function Documentation
|
builds a cluster starting from some node
Definition at line 105 of file SUMA_SurfClust.c. References BuildMethod, SUMA_CLUST_DATUM::centralnode, DListElmt_::data, SUMA_SURFCLUST_OPTIONS::DistLim, dlist_destroy(), dlist_head, dlist_tail, SUMA_OFFSET_LL_DATUM::layer, SUMA_GET_OFFSET_STRUCT::layers, LocalHead, SUMA_CLUST_DATUM::maxnode, SUMA_CLUST_DATUM::maxvalue, SUMA_CLUST_DATUM::minnode, SUMA_CLUST_DATUM::minvalue, SUMA_GET_OFFSET_STRUCT::N_layers, SUMA_CLUST_DATUM::N_Node, SUMA_SurfaceObject::N_Node, SUMA_NODE_NEIGHB_LAYER::N_NodesInLayer, DListElmt_::next, SUMA_OFFSET_LL_DATUM::ni, SUMA_CLUST_DATUM::NodeList, SUMA_NODE_NEIGHB_LAYER::NodesInLayer, SUMA_OFFSET_LL_DATUM::off, SUMA_GET_OFFSET_STRUCT::OffVect, SUMA_Boolean, SUMA_ENTRY, SUMA_free, SUMA_Free_getoffsets(), SUMA_getoffsets2(), SUMA_getoffsets_ll(), SUMA_Initialize_getoffsets(), SUMA_malloc, SUMA_OFFSETS2, SUMA_OFFSETS_LL, SUMA_RETURN, SUMA_ShowOffset_Info(), SUMA_ShowOffset_ll_Info(), SUMA_SL_Crit, SUMA_SL_Err, SUMA_CLUST_DATUM::totalabsvalue, SUMA_CLUST_DATUM::totalarea, SUMA_CLUST_DATUM::totalvalue, SUMA_CLUST_DATUM::ValueList, SUMA_CLUST_DATUM::varvalue, and SUMA_CLUST_DATUM::weightedcentralnode. Referenced by SUMA_FindClusters().
00108 { 00109 static char FuncName[]={"SUMA_Build_Cluster_From_Node"}; 00110 SUMA_CLUST_DATUM *Clust = NULL; 00111 static int ncall; 00112 int il, jl, neighb; 00113 SUMA_GET_OFFSET_STRUCT *OffS = NULL; 00114 DList *offlist = NULL; 00115 DListElmt *elm = NULL; 00116 SUMA_OFFSET_LL_DATUM *dat=NULL; 00117 int NewClust = 0; 00118 SUMA_Boolean LocalHead = NOPE; 00119 00120 SUMA_ENTRY; 00121 ++ncall; 00122 if (dothisnode < 0) { 00123 SUMA_SL_Err("Unexpected negative index."); 00124 SUMA_RETURN(NULL); 00125 } 00126 if (!AddToThisClust) { 00127 Clust = (SUMA_CLUST_DATUM *)SUMA_malloc(sizeof(SUMA_CLUST_DATUM)); 00128 Clust->N_Node = 0; Clust->totalarea = 0.0; /* Clust->rank = -1; */ 00129 Clust->totalvalue = 0.0; Clust->totalabsvalue = 0.0; 00130 Clust->minvalue = ToBeAssigned[dothisnode]; Clust->minnode = dothisnode; 00131 Clust->maxvalue = ToBeAssigned[dothisnode]; Clust->maxnode = dothisnode; 00132 Clust->varvalue = 0.0; Clust->centralnode = 0; Clust->weightedcentralnode = 0; 00133 Clust->NodeList = (int *)SUMA_malloc((*N_TobeAssigned) * sizeof(int)); 00134 Clust->ValueList = (float *)SUMA_malloc((*N_TobeAssigned) * sizeof(float)); 00135 if (!Clust->NodeList || !Clust->ValueList) { 00136 SUMA_SL_Crit("Failed to allocate for NodeList or ValueList"); 00137 SUMA_free(Clust); Clust = NULL; 00138 SUMA_RETURN(NULL); 00139 } 00140 NewClust = 1; 00141 if (LocalHead) fprintf (SUMA_STDERR,"%s: New Cluster %p, with node %d\n", FuncName, Clust, dothisnode); 00142 } else { 00143 NewClust = 0; 00144 Clust = AddToThisClust; 00145 if (LocalHead) fprintf (SUMA_STDERR,"%s: Reusing Cluster %p, with node %d\n", FuncName, Clust, dothisnode); 00146 } 00147 00148 /* Add node to cluster */ 00149 if (LocalHead) fprintf(SUMA_STDERR,"%s: Adding node %d to cluster %p of %d nodes\n", FuncName, dothisnode, Clust, Clust->N_Node); 00150 Clust->NodeList[Clust->N_Node] = dothisnode; 00151 Clust->totalarea += NodeArea[dothisnode]; 00152 Clust->totalvalue += ToBeAssigned[dothisnode]; 00153 Clust->totalabsvalue += (float)fabs((float)ToBeAssigned[dothisnode]); 00154 if (ToBeAssigned[dothisnode] < Clust->minvalue) { Clust->minvalue = ToBeAssigned[dothisnode]; Clust->minnode = dothisnode; } 00155 if (ToBeAssigned[dothisnode] > Clust->maxvalue) { Clust->maxvalue = ToBeAssigned[dothisnode]; Clust->maxnode = dothisnode; } 00156 Clust->ValueList[Clust->N_Node] = ToBeAssigned[dothisnode]; 00157 ++Clust->N_Node; 00158 00159 /* mark it as assigned, an reduce the number of nodes left to assign*/ 00160 ToBeAssigned[dothisnode] = 0; --(*N_TobeAssigned); 00161 00162 if (BuildMethod == SUMA_OFFSETS2) { 00163 /* Tres bad memory utilization due to recursive calls */ 00164 if (*N_TobeAssigned) { 00165 /* look in its vicinity - bad memory usage due to recursive calls*/ 00166 OffS = SUMA_Initialize_getoffsets (SO->N_Node); 00167 SUMA_getoffsets2 (dothisnode, SO, Opt->DistLim, OffS, NULL, 0); 00168 #if 0 00169 if (NewClust) { 00170 FILE *fid=NULL; 00171 char *s=NULL, tmp[50]; 00172 fid = fopen("offsets2.1D", "w"); 00173 if (!fid) { 00174 SUMA_SL_Err("Could not open file for writing.\nCheck file permissions, disk space.\n"); 00175 } else { 00176 s = SUMA_ShowOffset_Info(OffS, 0); 00177 if (s) { fprintf(fid,"%s\n", s); SUMA_free(s); s = NULL;} 00178 fclose(fid); 00179 } 00180 } 00181 #endif 00182 /* search to see if any are to be assigned */ 00183 for (il=1; il<OffS->N_layers; ++il) { /* starting at layer 1, layer 0 is the node itself */ 00184 for (jl=0; jl<OffS->layers[il].N_NodesInLayer; ++jl) { 00185 neighb = OffS->layers[il].NodesInLayer[jl]; 00186 if (ToBeAssigned[neighb] && OffS->OffVect[neighb] <= Opt->DistLim) { 00187 /* take that node into the cluster */ 00188 SUMA_Build_Cluster_From_Node( neighb, Clust, ToBeAssigned, N_TobeAssigned, NodeArea, SO, Opt); 00189 } 00190 } 00191 } 00192 /* free this OffS structure (Note you can't recycle the same structure because you are using many 00193 OffS at one because of recursive calls */ 00194 if (OffS) SUMA_Free_getoffsets(OffS); OffS = NULL; 00195 } 00196 } else if (BuildMethod == SUMA_OFFSETS_LL) { 00197 if (*N_TobeAssigned) { 00198 /* look in its vicinity */ 00199 if (!(offlist = SUMA_getoffsets_ll (dothisnode, SO, Opt->DistLim, NULL, 0))) { 00200 SUMA_SL_Err("Failed to get offsets.\nNo cleanup done."); 00201 SUMA_RETURN(NULL); 00202 } 00203 #if 0 00204 if (NewClust) { 00205 FILE *fid=NULL; 00206 char *s=NULL, tmp[50]; 00207 fid = fopen("offsets_ll.1D", "w"); 00208 if (!fid) { 00209 SUMA_SL_Err("Could not open file for writing.\nCheck file permissions, disk space.\n"); 00210 } else { 00211 s = SUMA_ShowOffset_ll_Info(offlist, 0); 00212 if (s) { fprintf(fid,"%s\n", s); SUMA_free(s); s = NULL;} 00213 fclose(fid); 00214 } 00215 } 00216 #endif 00217 00218 /* search to see if any are to be assigned, start at layer 1*/ 00219 elm = dlist_head(offlist); 00220 dat = (SUMA_OFFSET_LL_DATUM *)elm->data; 00221 if (dat->layer != 0) { 00222 SUMA_SL_Err("Unexpected non zero layer for first element."); 00223 SUMA_RETURN(NULL); 00224 } 00225 do { 00226 elm = elm->next; 00227 dat = (SUMA_OFFSET_LL_DATUM *)elm->data; 00228 neighb = dat->ni; 00229 if (ToBeAssigned[neighb] && dat->off <= Opt->DistLim) { 00230 /* take that node into the cluster */ 00231 SUMA_Build_Cluster_From_Node( neighb, Clust, ToBeAssigned, N_TobeAssigned, NodeArea, SO, Opt); 00232 } 00233 } while (elm != dlist_tail(offlist)); 00234 dlist_destroy(offlist); 00235 } 00236 } 00237 00238 /* If you ever use this function again, you should probably SUMA_free(offlist); dlist_destroy(candlist); SUMA_free(candlist); */ 00239 00240 SUMA_RETURN(Clust); 00241 } |
|
builds a cluster starting from some node
Definition at line 273 of file SUMA_SurfClust.c. References SUMA_CLUST_DATUM::centralnode, DListElmt_::data, SUMA_SURFCLUST_OPTIONS::DistLim, dlist_destroy(), dlist_head, dlist_init(), dlist_ins_next(), dlist_remove(), dlist_size, dlist_tail, itmp, SUMA_GET_OFFSET_STRUCT::layers, LocalHead, SUMA_CLUST_DATUM::maxnode, SUMA_CLUST_DATUM::maxvalue, SUMA_CLUST_DATUM::minnode, SUMA_CLUST_DATUM::minvalue, SUMA_GET_OFFSET_STRUCT::N_layers, SUMA_SurfaceObject::N_Node, SUMA_CLUST_DATUM::N_Node, SUMA_NODE_NEIGHB_LAYER::N_NodesInLayer, SUMA_CLUST_DATUM::NodeList, SUMA_NODE_NEIGHB_LAYER::NodesInLayer, SUMA_GET_OFFSET_STRUCT::OffVect, SUMA_ADD_NODE_TO_CLUST, SUMA_Boolean, SUMA_calloc, SUMA_ENTRY, SUMA_free, SUMA_Free_getoffsets(), SUMA_getoffsets2(), SUMA_Initialize_getoffsets(), SUMA_malloc, SUMA_Recycle_getoffsets(), SUMA_RETURN, SUMA_SL_Crit, SUMA_SL_Err, SUMA_CLUST_DATUM::totalabsvalue, SUMA_CLUST_DATUM::totalarea, SUMA_CLUST_DATUM::totalvalue, SUMA_SURFCLUST_OPTIONS::update, SUMA_CLUST_DATUM::ValueList, SUMA_CLUST_DATUM::varvalue, and SUMA_CLUST_DATUM::weightedcentralnode. Referenced by SUMA_FindClusters().
00276 { 00277 static char FuncName[]={"SUMA_Build_Cluster_From_Node_NoRec"}; 00278 SUMA_CLUST_DATUM *Clust = NULL; 00279 static int ncall; 00280 static int N_Orig = -1; 00281 int il, jl, neighb, itmp; 00282 SUMA_GET_OFFSET_STRUCT *OffS = NULL; 00283 DList *offlist = NULL, *candlist=NULL; 00284 DListElmt *elm = NULL, *dothiselm=NULL; 00285 SUMA_OFFSET_LL_DATUM *dat=NULL; 00286 int NewClust = 0; 00287 byte *visited=NULL; 00288 SUMA_Boolean LocalHead = NOPE; 00289 00290 SUMA_ENTRY; 00291 ++ncall; 00292 /* a trick to know when to initialize */ 00293 if (Opt->update < 0) { N_Orig = *N_TobeAssigned; Opt->update = -Opt->update; } 00294 00295 if (dothisnode < 0) { 00296 SUMA_SL_Err("Unexpected negative index."); 00297 SUMA_RETURN(NULL); 00298 } 00299 00300 OffS = SUMA_Initialize_getoffsets (SO->N_Node); 00301 Clust = (SUMA_CLUST_DATUM *)SUMA_malloc(sizeof(SUMA_CLUST_DATUM)); 00302 Clust->N_Node = 0; Clust->totalarea = 0.0; /* Clust->rank = -1; */ 00303 Clust->totalvalue = 0.0; Clust->totalabsvalue = 0.0; 00304 Clust->minvalue = ToBeAssigned[dothisnode]; Clust->minnode = dothisnode; 00305 Clust->maxvalue = ToBeAssigned[dothisnode]; Clust->maxnode = dothisnode; 00306 Clust->varvalue = 0.0; Clust->centralnode = 0; Clust->weightedcentralnode = 0; 00307 Clust->NodeList = (int *)SUMA_malloc((*N_TobeAssigned) * sizeof(int)); 00308 Clust->ValueList = (float *)SUMA_malloc((*N_TobeAssigned) * sizeof(float)); 00309 if (!Clust->NodeList || !Clust->ValueList || !OffS) { 00310 SUMA_SL_Crit("Failed to allocate for NodeList or ValueList"); 00311 SUMA_free(Clust); Clust = NULL; 00312 SUMA_RETURN(NULL); 00313 } 00314 candlist = (DList*)SUMA_malloc(sizeof(DList)); 00315 visited = (byte *)SUMA_calloc(SO->N_Node, sizeof(byte)); 00316 if (!visited || !candlist) { 00317 SUMA_SL_Crit("Failed to allocate for visited or candlist"); 00318 SUMA_free(Clust); Clust = NULL; 00319 SUMA_RETURN(NULL); 00320 } 00321 dlist_init(candlist, NULL); 00322 /* Add node to cluster */ 00323 SUMA_ADD_NODE_TO_CLUST(dothisnode, Clust, NodeArea, ToBeAssigned); 00324 /* mark it as assigned, an reduce the number of nodes left to assign*/ 00325 ToBeAssigned[dothisnode] = 0; --(*N_TobeAssigned); 00326 visited[dothisnode] = YUP; 00327 dlist_ins_next(candlist, dlist_tail(candlist), (void *)dothisnode); 00328 while (*N_TobeAssigned && dlist_size(candlist)) { 00329 /* look in its vicinity */ 00330 dothiselm = dlist_head(candlist); dothisnode = (int) dothiselm->data; 00331 SUMA_getoffsets2 (dothisnode, SO, Opt->DistLim, OffS, NULL, 0); 00332 /* remove node from candidate list */ 00333 dlist_remove(candlist, dothiselm, (void*)&itmp); 00334 /* search to see if any are to be assigned */ 00335 for (il=1; il<OffS->N_layers; ++il) { /* starting at layer 1, layer 0 is the node itself */ 00336 for (jl=0; jl<OffS->layers[il].N_NodesInLayer; ++jl) { 00337 neighb = OffS->layers[il].NodesInLayer[jl]; 00338 if (ToBeAssigned[neighb] && OffS->OffVect[neighb] <= Opt->DistLim) { 00339 /* take that node into the cluster */ 00340 SUMA_ADD_NODE_TO_CLUST(neighb, Clust, NodeArea, ToBeAssigned); 00341 /* mark it as assigned, an reduce the number of nodes left to assign*/ 00342 ToBeAssigned[neighb] = 0; --(*N_TobeAssigned); 00343 if (Opt->update) { 00344 if (N_Orig - *N_TobeAssigned >= Opt->update) { 00345 if (LocalHead) fprintf(SUMA_STDERR,"%s: tick (%d nodes processed)\n", FuncName, N_Orig - *N_TobeAssigned); 00346 else fprintf(SUMA_STDERR,"."); 00347 00348 N_Orig = *N_TobeAssigned; 00349 } 00350 } 00351 /* mark it as a candidate if it has not been visited as a candidate before */ 00352 if (!visited[neighb]) { 00353 dlist_ins_next(candlist, dlist_tail(candlist), (void *)neighb); 00354 visited[neighb] = YUP; 00355 } 00356 00357 } 00358 } 00359 } 00360 /* recycle */ 00361 SUMA_Recycle_getoffsets (OffS); 00362 } 00363 /* free this OffS structure */ 00364 if (OffS) SUMA_Free_getoffsets(OffS); OffS = NULL; 00365 if (Opt->update) fprintf(SUMA_STDERR,"\n"); 00366 /* destroy the list */ 00367 if (candlist) { dlist_destroy(candlist); SUMA_free(candlist); candlist = NULL; } 00368 SUMA_RETURN(Clust); 00369 } |
|
Calculate area of each node as one third of the sum of the areas of incident triangles. If you change this function make sure changes are also done on RickR's compute_node_areas since the two functions use the same principle.
Definition at line 51 of file SUMA_SurfClust.c. References c, SUMA_CommonFields::DsetList, i, SUMA_SurfaceObject::MF, SUMA_MEMBER_FACE_SETS::N_Memb, SUMA_SurfaceObject::N_Node, SUMA_MEMBER_FACE_SETS::NodeMemberOfFaceSet, SUMA_SurfaceObject::PolyArea, SUMA_ENTRY, SUMA_malloc, SUMA_RETURN, SUMA_SL_Crit, and SUMA_SurfaceMetrics_eng().
00052 { 00053 static char FuncName[]={"SUMA_CalculateNodeAreas"}; 00054 float *NodeAreas=NULL; 00055 int *flist = NULL, i, c; 00056 00057 SUMA_ENTRY; 00058 00059 if (!SO) { SUMA_RETURN(NodeAreas); } 00060 if (!SO->PolyArea) { 00061 if (!SUMA_SurfaceMetrics_eng(SO, "PolyArea", NULL, 0, SUMAg_CF->DsetList)) { 00062 fprintf (SUMA_STDERR,"Error %s: Failed in SUMA_SurfaceMetrics.\n", FuncName); 00063 SUMA_RETURN(NodeAreas); 00064 } 00065 } 00066 00067 NodeAreas = (float *)SUMA_malloc(SO->N_Node*sizeof(float)); 00068 if (!NodeAreas) { SUMA_SL_Crit ("Failed to allocate for NodeAreas"); SUMA_RETURN(NodeAreas); } 00069 00070 for (i=0; i<SO->N_Node; ++i) { 00071 flist = SO->MF->NodeMemberOfFaceSet[i]; 00072 NodeAreas[i] = 0.0; 00073 for (c = 0; c < SO->MF->N_Memb[i]; c++) { 00074 NodeAreas[i] += SO->PolyArea[flist[c]]; 00075 } 00076 NodeAreas[i] /= 3.0; 00077 } 00078 00079 SUMA_RETURN(NodeAreas); 00080 } |
|
Finds a node that best approximates the property of the center of mass on the surface. Note that the real center of mass of a curved surface is rarely on the surface, so this is an attempt at localizing a node that is central to an ROI and that can reflect the weight, or activity, distribution in that ROI.
Definition at line 789 of file SUMA_SurfClust.c. References c, SUMA_CLUST_DATUM::centralnode, i, LocalHead, SUMA_OFFSET_STRUCT::N_Neighb, SUMA_CLUST_DATUM::N_Node, SUMA_SurfaceObject::N_Node, nc, SUMA_OFFSET_STRUCT::Neighb_dist, SUMA_OFFSET_STRUCT::Neighb_ind, SUMA_CLUST_DATUM::NodeList, SUMA_SurfaceObject::NodeList, SUMA_Boolean, SUMA_calloc, SUMA_ENTRY, SUMA_free, SUMA_Free_getoffsets(), SUMA_GetOffset2Offset(), SUMA_getoffsets2(), SUMA_Initialize_getoffsets(), SUMA_malloc, SUMA_NORM_VEC, SUMA_RETURN, SUMA_SL_Crit, SUMA_SL_Err, SUMA_SL_Note, SUMA_UNIT_VEC, SUMA_CLUST_DATUM::ValueList, and SUMA_CLUST_DATUM::weightedcentralnode. Referenced by SUMA_FindClusters().
00790 { 00791 static char FuncName[]={"SUMA_ClusterCenterofMass"}; 00792 SUMA_GET_OFFSET_STRUCT *OffS = NULL; 00793 SUMA_OFFSET_STRUCT OS; 00794 int *CoverThisNode = NULL, i, c, ni, nc, centralnode, weightedcentralnode, 00795 nanch, k, WeightByValue = 1; 00796 float Uia[3], dia, Uca[3], dca, s[3], s_w[3], *DistVec=NULL, 00797 *weightedcentrality=NULL, minweightedcentrality = 0.0, *centrality=NULL, 00798 mincentrality = 0.0, mtotal_w, mi_w, fac, mtotal, mi; 00799 static int ncall; 00800 SUMA_Boolean LocalHead = NOPE; 00801 00802 SUMA_ENTRY; 00803 00804 centralnode = -1; 00805 weightedcentralnode = -1; 00806 if (!SO || !cd) { SUMA_RETURN(NOPE); } 00807 if (!cd->N_Node || !cd->NodeList) { SUMA_RETURN(NOPE); } 00808 OffS = SUMA_Initialize_getoffsets (SO->N_Node); 00809 if (!OffS) { 00810 SUMA_SL_Err("Failed to allocate for OffS"); 00811 SUMA_RETURN(NOPE); 00812 } 00813 00814 CoverThisNode = (int *)SUMA_calloc(SO->N_Node, sizeof(int)); 00815 if (!CoverThisNode) { 00816 SUMA_SL_Crit("Failed to allocate for CoverThisNode"); 00817 SUMA_RETURN(NOPE); 00818 } 00819 if (cd->N_Node == SO->N_Node) { 00820 /* not much to do, return 0 */ 00821 SUMA_SL_Note("Cluster spans entire surface.\nNo central node.\n"); 00822 cd->centralnode = 0; 00823 cd->weightedcentralnode = 0; 00824 SUMA_RETURN(YUP); 00825 } 00826 00827 for (i=0; i<cd->N_Node; ++i) { CoverThisNode[cd->NodeList[i]] = 1; } 00828 nanch = cd->NodeList[0]; /* anchor node */ 00829 SUMA_getoffsets2 (cd->NodeList[0], SO, 0, OffS, CoverThisNode, cd->N_Node); 00830 /* help me with a nicer structure (for sanity)*/ 00831 if (!SUMA_GetOffset2Offset (OffS, &OS)) { 00832 SUMA_SL_Err("Failed in SUMA_GetOffset2Offset"); 00833 SUMA_RETURN(NOPE); 00834 } 00835 if (OffS) SUMA_Free_getoffsets(OffS); OffS = NULL; 00836 /* put the distance in an easy to search array */ 00837 DistVec = (float *) SUMA_calloc(SO->N_Node, sizeof(float)); 00838 centrality = (float *)SUMA_malloc(OS.N_Neighb * sizeof(float)); 00839 weightedcentrality = (float *)SUMA_malloc(OS.N_Neighb * sizeof(float)); 00840 if (!DistVec || !centrality || !weightedcentrality) { 00841 SUMA_SL_Crit("Failed to allocate."); 00842 SUMA_RETURN(NOPE); 00843 } 00844 for (c=0; c < OS.N_Neighb; ++c) { DistVec[OS.Neighb_ind[c]] = OS.Neighb_dist[c]; } 00845 00846 /* Now calculate the center of massity of each node 00847 This is no center of mass in the proper definition of the term*/ 00848 00849 #if 1 00850 if (cd->N_Node == 1) { 00851 centralnode = cd->NodeList[0]; 00852 weightedcentralnode = cd->NodeList[0]; 00853 } else { 00854 for (c=0; c < OS.N_Neighb; ++c) { 00855 nc = OS.Neighb_ind[c]; /* Node index into SO of center node */ 00856 s[0] = s[1] = s[2] = 0.0; s_w[0] = s_w[1] = s_w[2] = 0.0; 00857 centrality[c] = 0.0; weightedcentrality[c] = 0.0; mtotal_w = 0.0; /* recalculated each time, not a big deal ... */ 00858 for (i=0; i<cd->N_Node; ++i) { 00859 mi_w = cd->ValueList[i]; 00860 mtotal_w += mi_w; 00861 ni = cd->NodeList[i]; /* Node index into SO of other node in cluster */ 00862 SUMA_UNIT_VEC((&(SO->NodeList[3*ni])), (&(SO->NodeList[3*nanch])), Uia, dia); 00863 if (UseSurfDist) { for (k=0; k<3;++k) { fac = Uia[k] * DistVec[ni]; s_w[k] += mi_w * fac; s[k] += fac;} } 00864 else { for (k=0; k<3;++k) { fac = Uia[k] * dia; s_w[k] += mi_w * fac; s[k] += fac; } } 00865 } 00866 SUMA_UNIT_VEC((&(SO->NodeList[3*nc])), (&(SO->NodeList[3*nanch])), Uca, dca); 00867 if (UseSurfDist) { for (k=0; k<3;++k) { fac = Uca[k] * DistVec[nc]; s_w[k] -= mtotal_w * fac; s[k] -= cd->N_Node * fac; } } 00868 else { for (k=0; k<3;++k) { fac = Uca[k] * dca; s_w[k] -= mtotal_w * fac; s[k] -= cd->N_Node * fac;} } 00869 00870 SUMA_NORM_VEC(s, 3, centrality[c]); SUMA_NORM_VEC(s_w, 3, weightedcentrality[c]); 00871 if (LocalHead) fprintf(SUMA_STDERR,"%s: call %d, Centrality of node %d / %d = %f , weighted %f\n", FuncName, ncall, nc, nanch, centrality[c], weightedcentrality[c]); 00872 if (c == 0) { 00873 mincentrality = centrality[c]; centralnode = nc; 00874 minweightedcentrality = weightedcentrality[c]; weightedcentralnode = nc; 00875 } else { 00876 if (centrality[c] < mincentrality) { mincentrality = centrality[c]; centralnode = nc; } 00877 if (weightedcentrality[c] < minweightedcentrality) { minweightedcentrality = weightedcentrality[c]; weightedcentralnode = nc; } 00878 } 00879 00880 } 00881 } 00882 cd->centralnode = centralnode; 00883 cd->weightedcentralnode = weightedcentralnode; 00884 if (LocalHead) fprintf(SUMA_STDERR,"%s: Central node chosen %d, weighted %d\n", FuncName, cd->centralnode, cd->weightedcentralnode); 00885 #else 00886 if (cd->N_Node == 1) { 00887 centralnode = cd->NodeList[0]; 00888 } else { 00889 for (c=0; c < OS.N_Neighb; ++c) { 00890 nc = OS.Neighb_ind[c]; /* Node index into SO of center node */ 00891 s[0] = s[1] = s[2] = 0.0; 00892 centrality[c] = 0.0; mtotal = 0.0; /* recalculated each time, not a big deal ... */ 00893 for (i=0; i<cd->N_Node; ++i) { 00894 if (WeightByValue) mi = cd->ValueList[i]; 00895 else mi = 1.0; 00896 mtotal += mi; 00897 ni = cd->NodeList[i]; /* Node index into SO of other node in cluster */ 00898 SUMA_UNIT_VEC((&(SO->NodeList[3*ni])), (&(SO->NodeList[3*nanch])), Uia, dia); 00899 if (UseSurfDist) { for (k=0; k<3;++k) s[k] += mi * Uia[k] * DistVec[ni]; } 00900 else { for (k=0; k<3;++k) s[k] += mi * Uia[k] * dia; } 00901 } 00902 SUMA_UNIT_VEC((&(SO->NodeList[3*nc])), (&(SO->NodeList[3*nanch])), Uca, dca); 00903 if (UseSurfDist) { for (k=0; k<3;++k) s[k] -= mtotal * Uca[k] * DistVec[nc]; } 00904 else { for (k=0; k<3;++k) s[k] -= mtotal * Uca[k] * dca; } 00905 00906 SUMA_NORM_VEC(s, 3, centrality[c]); 00907 if (LocalHead) fprintf(SUMA_STDERR,"%s: call %d, Centrality of node %d / %d = %f\n", FuncName, ncall, nc, nanch, centrality[c]); 00908 if (c == 0) { mincentrality = centrality[c]; centralnode = nc; } 00909 else if (centrality[c] < mincentrality) { mincentrality = centrality[c]; centralnode = nc; } 00910 } 00911 } 00912 cd->centralnode = centralnode; 00913 if (LocalHead) fprintf(SUMA_STDERR,"%s: Central node chosen %d\n", FuncName, cd->centralnode); 00914 cd->weightedcentralnode = -1; 00915 #endif 00916 00917 if (CoverThisNode) SUMA_free(CoverThisNode); CoverThisNode = NULL; 00918 if (OS.Neighb_dist) SUMA_free(OS.Neighb_dist); OS.Neighb_dist = NULL; 00919 if (OS.Neighb_ind) SUMA_free(OS.Neighb_ind); OS.Neighb_ind = NULL; 00920 if (DistVec) SUMA_free(DistVec); DistVec = NULL; 00921 if (centrality) SUMA_free(centrality); centrality = NULL; 00922 if (weightedcentrality) SUMA_free(weightedcentrality); weightedcentrality = NULL; 00923 00924 ++ncall; 00925 SUMA_RETURN(YUP); 00926 } |
|
Finds clusters of data on the surface.
Definition at line 389 of file SUMA_SurfClust.c. References SUMA_SURFCLUST_OPTIONS::AreaLim, BuildMethod, dlist_init(), dlist_ins_next(), dlist_tail, SUMA_SURFCLUST_OPTIONS::DoCentrality, i, LocalHead, SUMA_SurfaceObject::N_Node, SUMA_CLUST_DATUM::N_Node, nc, SUMA_CLUST_DATUM::NodeList, SUMA_Boolean, SUMA_Build_Cluster_From_Node(), SUMA_Build_Cluster_From_Node_NoRec(), SUMA_calloc, SUMA_ClusterCenterofMass(), SUMA_ENTRY, SUMA_free, SUMA_FreeClustDatum(), SUMA_LH, SUMA_malloc, SUMA_OFFSETS2, SUMA_OFFSETS2_NO_REC, SUMA_OFFSETS_LL, SUMA_realloc, SUMA_RETURN, SUMA_S_Err, SUMA_SL_Crit, SUMA_SL_Err, SUMA_SL_Note, SUMA_CLUST_DATUM::totalarea, SUMA_CLUST_DATUM::totalvalue, SUMA_SURFCLUST_OPTIONS::update, SUMA_CLUST_DATUM::ValueList, and SUMA_CLUST_DATUM::varvalue.
00392 { 00393 static char FuncName[]={"SUMA_FindClusters"}; 00394 DList *list=NULL; 00395 DListElmt *elm=NULL; 00396 float *ToBeAssigned=NULL; 00397 float mean; 00398 int N_n, nc, i, kk, PureNothing=0; 00399 SUMA_CLUST_DATUM *Clust = NULL; 00400 SUMA_Boolean LocalHead = NOPE; 00401 00402 SUMA_ENTRY; 00403 00404 if (!SO || !nv || !ni) { 00405 SUMA_S_Err("Bad parameters"); 00406 } 00407 if (dothisnode == -1) { /* initialize */ 00408 SUMA_LH("Initializing"); 00409 nc = 0; 00410 /* initialize the list */ 00411 list = (DList *)SUMA_malloc(sizeof(DList)); 00412 dlist_init(list, SUMA_FreeClustDatum); 00413 ToBeAssigned = (float *)SUMA_calloc(SO->N_Node, sizeof(float)); 00414 N_n = N_ni; 00415 for (i=0; i<N_n; ++i) { 00416 if (!nv[i]) { 00417 ++PureNothing; 00418 } 00419 ToBeAssigned[ni[i]] = nv[i]; 00420 } 00421 if (Opt->update) { 00422 fprintf(SUMA_STDERR,"%s: Have %d nodes to work with. %d nodes have 0 value.\n", FuncName, N_n, PureNothing); 00423 } 00424 } 00425 00426 while (N_n - PureNothing > 0) { 00427 dothisnode = -1; 00428 for (i=0;i<SO->N_Node; ++i) { 00429 if (ToBeAssigned[i]) { 00430 dothisnode = i; continue; 00431 } 00432 } 00433 if (dothisnode < 0) { 00434 SUMA_S_Err("Not expected here. dothisnode < 0"); 00435 SUMA_RETURN(list); 00436 } 00437 00438 if (BuildMethod == SUMA_OFFSETS2_NO_REC) { 00439 Clust = SUMA_Build_Cluster_From_Node_NoRec(dothisnode, ToBeAssigned, &N_n, NodeArea, SO, Opt); 00440 } else if (BuildMethod == SUMA_OFFSETS2 || BuildMethod == SUMA_OFFSETS_LL) { 00441 Clust = SUMA_Build_Cluster_From_Node(dothisnode, NULL, ToBeAssigned, &N_n, NodeArea, SO, Opt); 00442 } else { 00443 SUMA_SL_Err("No Such Method!"); 00444 SUMA_RETURN(list); 00445 } 00446 if (!Clust) { 00447 SUMA_SL_Err("Failed in SUMA_Build_Cluster_From_Node*"); 00448 SUMA_RETURN(list); 00449 } 00450 if (LocalHead) fprintf(SUMA_STDERR,"%s: Cluster %p is finished, %d nodes\n", FuncName, Clust, Clust->N_Node); 00451 00452 if (Opt->AreaLim > 0 && Clust->totalarea < Opt->AreaLim) { 00453 SUMA_LH("Cluster less than area limit"); 00454 SUMA_FreeClustDatum((void *)Clust); Clust = NULL; 00455 } else { 00456 mean = Clust->totalvalue/((float)Clust->N_Node); 00457 for (kk=0; kk < Clust->N_Node; ++kk) { 00458 Clust->varvalue += (Clust->ValueList[kk] - mean) * (Clust->ValueList[kk] - mean); 00459 } 00460 if (Clust->N_Node > 1) Clust->varvalue /= (Clust->N_Node - 1); 00461 else Clust->varvalue = 0.0; 00462 /* reallocate to save space */ 00463 Clust->NodeList = (int *)SUMA_realloc(Clust->NodeList, sizeof(int)*Clust->N_Node); 00464 Clust->ValueList = (float *)SUMA_realloc(Clust->ValueList, sizeof(float)*Clust->N_Node); 00465 if (!Clust->NodeList || !Clust->ValueList) { 00466 SUMA_SL_Crit("Failed to reallocate for NodeList or ValueList"); 00467 SUMA_RETURN(NULL); 00468 } 00469 /* find the central node */ 00470 if (Opt->DoCentrality) { 00471 if (Opt->update) { 00472 SUMA_SL_Note("Looking for central nodes...(use -no_cent to skip this slow step)"); 00473 } 00474 if (!SUMA_ClusterCenterofMass (SO, Clust, 1)) { 00475 SUMA_SL_Err("Failed to find central node"); 00476 SUMA_RETURN(list); 00477 } 00478 } 00479 00480 dlist_ins_next(list, dlist_tail(list), (void *)Clust); 00481 ++nc; 00482 } 00483 } 00484 00485 if (N_n == 0) { 00486 if (LocalHead) fprintf(SUMA_STDERR,"%s: No more nodes to consider, cleaning up.\n", FuncName); 00487 if (ToBeAssigned) SUMA_free(ToBeAssigned); ToBeAssigned = NULL; \ 00488 } 00489 00490 SUMA_RETURN(list); 00491 } |
|
Definition at line 29 of file SUMA_SurfClust.c. References SUMA_CLUST_DATUM::NodeList, SUMA_ENTRY, SUMA_free, SUMA_RETURNe, and SUMA_CLUST_DATUM::ValueList. Referenced by SUMA_FindClusters().
00030 { 00031 static char FuncName[]={"SUMA_FreeClustDatum"}; 00032 SUMA_CLUST_DATUM *Clust = NULL; 00033 SUMA_ENTRY; 00034 00035 if (!data) SUMA_RETURNe; 00036 Clust = (SUMA_CLUST_DATUM *)data; 00037 if (Clust->NodeList) SUMA_free(Clust->NodeList); 00038 if (Clust->ValueList) SUMA_free(Clust->ValueList); 00039 SUMA_free(Clust); 00040 00041 SUMA_RETURNe; 00042 } |
|
Masks a data set by a clustering list Definition at line 613 of file SUMA_SurfClust.c. References DListElmt_::data, dlist_head, dlist_tail, SUMA_DSET::dnel, i, LocalHead, SUMA_SurfaceObject::N_Node, SUMA_CLUST_DATUM::N_Node, DListElmt_::next, SUMA_CLUST_DATUM::NodeList, SDEST_VECLEN, SUMA_Boolean, SUMA_calloc, SUMA_ENTRY, SUMA_free, SUMA_GetNodeDef(), SUMA_isDsetColumn_inferred(), SUMA_MaskedCopyofDset(), SUMA_RETURN, SUMA_SL_Err, NI_element::vec_len, and NI_element::vec_num.
00614 { 00615 static char FuncName[]={"SUMA_MaskDsetByClustList"}; 00616 int i, j; 00617 DListElmt *elmt=NULL; 00618 SUMA_DSET *dset = NULL; 00619 int *ni=NULL, N_ni, cnt; 00620 SUMA_CLUST_DATUM *cd=NULL; 00621 byte *ismask=NULL, *rowmask=NULL, *colmask = NULL; 00622 SUMA_Boolean LocalHead = NOPE; 00623 00624 SUMA_ENTRY; 00625 00626 if (!list) { 00627 SUMA_SL_Err("NULL list"); 00628 SUMA_RETURN(dset); 00629 } 00630 /* which nodes in mask ? */ 00631 ismask = (byte *)SUMA_calloc(SO->N_Node, sizeof(byte)); /* you need to allocate for SO->N_Node, to be safe, otherwise you will need 00632 to search for the highest node index.. */ 00633 elmt = NULL; cnt = 0; 00634 do { 00635 if (!elmt) elmt = dlist_head(list); 00636 else elmt = elmt->next; 00637 cd = (SUMA_CLUST_DATUM *)elmt->data; 00638 for (j=0; j<cd->N_Node; ++j) { 00639 if(LocalHead) fprintf (SUMA_STDERR,"nic=%d\t", cd->NodeList[j]); 00640 ismask[cd->NodeList[j]] = 1; 00641 ++cnt; 00642 } 00643 } while (elmt != dlist_tail(list)); 00644 if (LocalHead) fprintf(SUMA_STDERR,"%s:\n%d nodes in cluster list.\n", FuncName, cnt); 00645 00646 /* now form a rowmask vector to parallel rows in idset */ 00647 rowmask = (byte *)SUMA_calloc(idset->dnel->vec_len, sizeof(byte)); 00648 colmask = (byte *)SUMA_calloc(idset->dnel->vec_num, sizeof(byte)); 00649 00650 /* get the node index column in idset */ 00651 ni = SUMA_GetNodeDef(idset); 00652 N_ni = SDEST_VECLEN(idset); 00653 if (!ni) { 00654 SUMA_SL_Err("Failed to find node index column"); 00655 SUMA_RETURN(NULL); 00656 } 00657 /* now, fill rowmask */ 00658 for (i=0; i<idset->dnel->vec_len; ++i) { if (ismask[ni[i]]) { rowmask[i]=1; if(LocalHead) fprintf (SUMA_STDERR,"%d,%d\t", ni[i], i); } } 00659 /* fill colmask*/ 00660 for (i=0; i<idset->dnel->vec_num; ++i) { 00661 if (SUMA_isDsetColumn_inferred(idset, i)) { 00662 colmask[i]=0; 00663 if (LocalHead) fprintf(SUMA_STDERR,"%s: Column %d will not be written because it is inferred.\n", FuncName, i); 00664 } else colmask[i]=1; 00665 } 00666 00667 dset = SUMA_MaskedCopyofDset(idset, rowmask, colmask, !FullList, 1); 00668 if (!dset) { 00669 SUMA_SL_Err("Failed to create masked copy of input"); 00670 SUMA_RETURN(NULL); 00671 } 00672 00673 if (rowmask) SUMA_free(rowmask); rowmask = NULL; 00674 if (colmask) SUMA_free(colmask); colmask = NULL; 00675 if (ismask) SUMA_free(ismask); ismask = NULL; 00676 00677 SUMA_RETURN (dset); 00678 } |
|
Show the ViewState structure Definition at line 494 of file SUMA_SurfClust.c. References SUMA_Boolean, SUMA_ENTRY, SUMA_free, SUMA_RETURN, SUMA_Show_SurfClust_list_Info(), and SUMA_SL_Err.
00495 { 00496 static char FuncName[]={"SUMA_Show_SurfClust_list"}; 00497 char *s = NULL; 00498 00499 SUMA_ENTRY; 00500 00501 if (Out == NULL) Out = stdout; 00502 00503 s = SUMA_Show_SurfClust_list_Info(list, detail, params); 00504 if (!s) { 00505 SUMA_SL_Err("Failed in SUMA_Show_SurfClust_list_Info"); 00506 SUMA_RETURN(NOPE); 00507 } else { 00508 fprintf(Out, "%s", s); 00509 SUMA_free(s); s = NULL; 00510 } 00511 00512 SUMA_RETURN(YUP); 00513 } |
|
Show the SurfClust list Definition at line 516 of file SUMA_SurfClust.c. References SUMA_CLUST_DATUM::centralnode, DListElmt_::data, dlist_head, dlist_tail, i, SUMA_CLUST_DATUM::maxnode, SUMA_CLUST_DATUM::maxvalue, SUMA_CLUST_DATUM::minnode, SUMA_CLUST_DATUM::minvalue, SUMA_CLUST_DATUM::N_Node, DListElmt_::next, SUMA_CLUST_DATUM::NodeList, DList_::size, SUMA_COUNTER_PLURAL, SUMA_COUNTER_SUFFIX, SUMA_ENTRY, SUMA_free, SUMA_pad_string(), SUMA_RETURN, SUMA_SS2S, SUMA_StringAppend(), SUMA_StringAppend_va(), SUMA_CLUST_DATUM::totalabsvalue, SUMA_CLUST_DATUM::totalarea, SUMA_CLUST_DATUM::totalvalue, SUMA_CLUST_DATUM::varvalue, and SUMA_CLUST_DATUM::weightedcentralnode. Referenced by SUMA_Show_SurfClust_list().
00517 { 00518 static char FuncName[]={"SUMA_Show_SurfClust_list_Info"}; 00519 int i, ic, max; 00520 SUMA_STRING *SS = NULL; 00521 DListElmt *elmt=NULL; 00522 SUMA_CLUST_DATUM *cd=NULL; 00523 char *s=NULL, *pad_str, str[20]; 00524 int lc[]= { 6, 6, 9, 9, 9, 6, 6, 9, 6, 9, 6, 9, 9 }; 00525 char Col[][12] = { {"# Rank"}, {"num Nd"}, {"Area"}, {"Mean"}, {"|Mean|"},{"Cent"}, {"W Cent"},{"Min V"}, {"Min Nd"}, {"Max V"}, {"Max Nd"} , {"Var"}, {"SEM"} }; 00526 SUMA_ENTRY; 00527 00528 SS = SUMA_StringAppend (NULL, NULL); 00529 00530 if (!list) { 00531 SS = SUMA_StringAppend (SS,"NULL list.\n"); 00532 SUMA_SS2S(SS,s); 00533 SUMA_RETURN(s); 00534 } 00535 00536 if (!list->size) { 00537 SS = SUMA_StringAppend (SS,"Empty list.\n"); 00538 SUMA_SS2S(SS,s); 00539 SUMA_RETURN(s); 00540 }else{ 00541 SS = SUMA_StringAppend_va (SS,"#Col. 0 = Rank \n" 00542 "#Col. 1 = Number of nodes\n" 00543 "#Col. 2 = Total area (units^2)\n" 00544 "#Col. 3 = Mean value\n" 00545 "#Col. 4 = Mean absolute value\n" 00546 "#Col. 5 = Central node\n" 00547 "#Col. 6 = Weighted central node\n" 00548 "#Col. 7 = Minimum value\n" 00549 "#Col. 8 = Minimum node\n" 00550 "#Col. 9 = Maximum value\n" 00551 "#Col. 10 = Maximum node\n" 00552 "#Col. 11 = Variance\n" 00553 "#Col. 12 = Standard error of the mean\n" 00554 "#Command history:\n" 00555 "#%s\n", params); 00556 00557 for (ic=0; ic<13; ++ic) { 00558 if (ic == 0) sprintf(str,"%s", Col[ic]); 00559 else sprintf(str,"%s", Col[ic]); 00560 pad_str = SUMA_pad_string(str, ' ', lc[ic], 0); 00561 SS = SUMA_StringAppend_va (SS,"%s ", pad_str); 00562 SUMA_free(pad_str); 00563 } 00564 SS = SUMA_StringAppend_va (SS,"\n"); 00565 if (detail == 1) { 00566 SS = SUMA_StringAppend_va (SS,"#Other columns: list of 5 first nodes in ROI.\n"); 00567 } 00568 if (detail == 2) { 00569 SS = SUMA_StringAppend_va (SS,"#Other columns: list all nodes in ROI.\n"); 00570 } 00571 if (detail > 0) { 00572 SS = SUMA_StringAppend_va (SS,"#A total of %d cluster%s were found.\n", list->size, SUMA_COUNTER_PLURAL(list->size)); 00573 } 00574 } 00575 00576 elmt = NULL; 00577 ic = 1; 00578 do { 00579 if (!elmt) elmt = dlist_head(list); else elmt = elmt->next; 00580 if (!elmt) SS = SUMA_StringAppend_va (SS,"#%d%s cluster element is NULL!\n", ic, SUMA_COUNTER_SUFFIX(ic)); 00581 else { 00582 cd = (SUMA_CLUST_DATUM *)elmt->data; 00583 if (detail > 0) SS = SUMA_StringAppend_va (SS,"#%d%s cluster\n", ic, SUMA_COUNTER_SUFFIX(ic)); 00584 SS = SUMA_StringAppend_va (SS,"%6d %6d %9.2f" 00585 " %9.3f %9.3f" 00586 " %6d %6d" 00587 " %9.3f %6d" 00588 " %9.3f %6d" 00589 " %9.3f %9.3f" 00590 , ic, cd->N_Node, cd->totalarea 00591 , cd->totalvalue/((float)cd->N_Node), cd->totalabsvalue/((float)cd->N_Node) 00592 , cd->centralnode, cd->weightedcentralnode 00593 , cd->minvalue, cd->minnode 00594 , cd->maxvalue, cd->maxnode 00595 , cd->varvalue, sqrt(cd->varvalue/cd->N_Node)); 00596 if (detail > 0) { 00597 if (detail == 1) { 00598 if (cd->N_Node < 5) max = cd->N_Node; else max = 5; 00599 } else max = cd->N_Node; 00600 for (i=0;i<max; ++i) SS = SUMA_StringAppend_va (SS,"%d\t", cd->NodeList[i]); 00601 } 00602 SS = SUMA_StringAppend(SS,"\n"); 00603 } 00604 ++ic; 00605 } while (elmt != dlist_tail(list)); 00606 00607 SUMA_SS2S(SS,s); 00608 00609 SUMA_RETURN (s); 00610 } |
|
Definition at line 928 of file SUMA_SurfClust.c. References DListElmt_::data, dlist_head, dlist_ins_prev(), dlist_remove(), dlist_tail, LocalHead, SUMA_CLUST_DATUM::N_Node, DListElmt_::next, DListElmt_::prev, r, SUMA_Boolean, SUMA_ENTRY, SUMA_RETURN, SUMA_S_Err, SUMA_SORT_CLUST_BY_AREA, SUMA_SORT_CLUST_BY_NUMBER_NODES, SUMA_SORT_CLUST_NO_SORT, SUMA_SORT_CLUST_NOT_SET, SUMA_SURF_CLUST_SORT_MODES, and SUMA_CLUST_DATUM::totalarea.
00929 { 00930 static char FuncName[]={"SUMA_Sort_ClustersList"}; 00931 DListElmt *elmt=NULL, *max_elmt=NULL, *elmt_comp=NULL; 00932 SUMA_CLUST_DATUM *cd=NULL, *cd_comp=NULL, *cd_max=NULL; 00933 int r = 0; 00934 SUMA_Boolean LocalHead = NOPE; 00935 00936 SUMA_ENTRY; 00937 00938 if (!list) { SUMA_RETURN(NOPE); } 00939 switch (SortMode) { 00940 case SUMA_SORT_CLUST_NOT_SET: 00941 SUMA_S_Err("Why are you calling me?"); 00942 SUMA_RETURN(NOPE); 00943 break; 00944 case SUMA_SORT_CLUST_NO_SORT: 00945 SUMA_RETURN(YUP); 00946 break; 00947 case SUMA_SORT_CLUST_BY_NUMBER_NODES: 00948 case SUMA_SORT_CLUST_BY_AREA: 00949 elmt = NULL; 00950 do { 00951 if (!elmt) elmt = dlist_head(list); 00952 else elmt = elmt->next; 00953 cd = (SUMA_CLUST_DATUM *)elmt->data; 00954 /* compare to all ahead of this element */ 00955 if (elmt != dlist_tail(list)) { 00956 max_elmt = elmt; cd_max = (SUMA_CLUST_DATUM *)max_elmt->data; elmt_comp = NULL; 00957 do { 00958 if (!elmt_comp) elmt_comp = elmt->next; 00959 else elmt_comp = elmt_comp->next; 00960 cd_comp = (SUMA_CLUST_DATUM *)elmt_comp->data; 00961 if (SortMode == SUMA_SORT_CLUST_BY_NUMBER_NODES) { 00962 if (cd_comp->N_Node > cd_max->N_Node) { max_elmt = elmt_comp; cd_max = (SUMA_CLUST_DATUM *)max_elmt->data; } 00963 }else if (SortMode == SUMA_SORT_CLUST_BY_AREA) { 00964 if (cd_comp->totalarea > cd_max->totalarea) { max_elmt = elmt_comp; cd_max = (SUMA_CLUST_DATUM *)max_elmt->data; } 00965 } 00966 } while (elmt_comp != dlist_tail(list)); 00967 if (max_elmt != elmt) { /* max is the real deal */ 00968 dlist_remove(list, max_elmt, (void *)(&cd_max)); 00969 dlist_ins_prev(list, elmt, (void *)cd_max); 00970 elmt = elmt->prev; /* continue from that one */ 00971 } 00972 } 00973 } while (elmt != dlist_tail(list)); 00974 SUMA_RETURN(YUP); 00975 break; 00976 default: 00977 break; 00978 } 00979 00980 00981 00982 SUMA_RETURN(YUP); 00983 } |
|
Turn the clusters to a cluster dataset mask Definition at line 680 of file SUMA_SurfClust.c. References DListElmt_::data, dlist_head, dlist_tail, i, LocalHead, SUMA_SurfaceObject::N_Node, SUMA_CLUST_DATUM::N_Node, DListElmt_::next, SUMA_CLUST_DATUM::NodeList, SUMA_AddDsetNelCol(), SUMA_Boolean, SUMA_CreateDsetPointer(), SUMA_ENTRY, SUMA_free, SUMA_LH, SUMA_malloc, SUMA_NODE_INDEX, SUMA_NODE_INT, SUMA_NODE_ROI, SUMA_RETURN, SUMA_SL_Crit, and SUMA_SL_Err.
00681 { 00682 static char FuncName[]={"SUMA_SurfClust_list_2_DsetMask"}; 00683 int i, ic, max, j, rank; 00684 DListElmt *elmt=NULL; 00685 SUMA_DSET *dset = NULL; 00686 int *NodeIndex=NULL, N_Node, *Val = NULL; 00687 SUMA_CLUST_DATUM *cd=NULL; 00688 SUMA_Boolean LocalHead = NOPE; 00689 00690 SUMA_ENTRY; 00691 00692 if (!list) { 00693 SUMA_SL_Err("NULL list"); 00694 SUMA_RETURN(dset); 00695 } 00696 if (FullList) N_Node = SO->N_Node; 00697 else { 00698 elmt = NULL; N_Node = 0; 00699 do { 00700 if (!elmt) elmt = dlist_head(list); 00701 else elmt = elmt->next; 00702 cd = (SUMA_CLUST_DATUM *)elmt->data; 00703 N_Node += cd->N_Node; 00704 } while (elmt != dlist_tail(list)); 00705 } 00706 NodeIndex = (int *)SUMA_malloc(N_Node*sizeof(int)); 00707 Val = (int *)SUMA_malloc(N_Node * sizeof(int)); 00708 if (!NodeIndex || !Val){ 00709 SUMA_SL_Crit("Failed to allocate NodeIndex and or Val"); 00710 SUMA_RETURN(dset); 00711 } 00712 if (FullList) { 00713 for (i=0; i<N_Node; ++i) { 00714 NodeIndex[i] = i; Val[i] = 0; 00715 } 00716 elmt = NULL; rank = 1; 00717 do { 00718 if (!elmt) elmt = dlist_head(list); 00719 else elmt = elmt->next; 00720 cd = (SUMA_CLUST_DATUM *)elmt->data; 00721 for (j=0; j<cd->N_Node; ++j) { 00722 Val[cd->NodeList[j]] = rank; 00723 } 00724 ++rank; 00725 } while (elmt != dlist_tail(list)); 00726 } else { 00727 elmt = NULL; rank = 1; i = 0; 00728 do { 00729 if (!elmt) elmt = dlist_head(list); 00730 else elmt = elmt->next; 00731 cd = (SUMA_CLUST_DATUM *)elmt->data; 00732 for (j=0; j<cd->N_Node; ++j) { 00733 Val[i] = rank; 00734 NodeIndex[i] = cd->NodeList[j]; 00735 ++i; 00736 } 00737 ++rank; 00738 } while (elmt != dlist_tail(list)); 00739 } 00740 00741 SUMA_LH("Creating dset pointer"); 00742 dset = SUMA_CreateDsetPointer( 00743 leName, /* usually the filename */ 00744 SUMA_NODE_ROI, /* mix and match */ 00745 NULL, /* no idcode, let the function create one from the filename*/ 00746 NULL, /* no domain str specified */ 00747 N_Node /* Number of nodes allocated for */ 00748 ); /* DO NOT free dset, it is store in DsetList */ 00749 00750 /* form the dataset */ 00751 SUMA_LH("Adding NodeDef column ..."); 00752 if (!SUMA_AddDsetNelCol ( dset, /* the famed nel */ 00753 "le Node Def", 00754 SUMA_NODE_INDEX, 00755 (void *)NodeIndex, 00756 NULL, 00757 1 00758 )) { 00759 fprintf (stderr,"Error %s:\nFailed in SUMA_AddNelCol", FuncName); 00760 SUMA_RETURN(NULL); 00761 } 00762 00763 if (!SUMA_AddDsetNelCol (dset, "Cluster Rank", SUMA_NODE_INT, (void *)Val, NULL ,1)) { 00764 fprintf (stderr,"Error %s:\nFailed in SUMA_AddNelCol", FuncName); 00765 SUMA_RETURN (NULL); 00766 } 00767 00768 if (NodeIndex) SUMA_free(NodeIndex); NodeIndex = NULL; 00769 if (Val) SUMA_free(Val); Val = NULL; 00770 00771 SUMA_RETURN (dset); 00772 } |
Variable Documentation
|
Definition at line 26 of file SUMA_SurfClust.c. Referenced by SUMA_Build_Cluster_From_Node(), and SUMA_FindClusters(). |
|
Global pointer to structure containing info common to all viewers Definition at line 19 of file SUMA_SurfClust.c. |
|
Global pointer to Displayable Object structure vector Definition at line 20 of file SUMA_SurfClust.c. |
|
Number of DOs stored in DOv Definition at line 23 of file SUMA_SurfClust.c. |
|
Number of SVs stored in SVv Definition at line 22 of file SUMA_SurfClust.c. |
|
Global pointer to the vector containing the various Surface Viewer Structures Definition at line 21 of file SUMA_SurfClust.c. |