00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028 #include "AtomSel.h"
00029 #include "VMDApp.h"
00030 #include "MoleculeList.h"
00031 #include "Molecule.h"
00032 #include "VolumetricData.h"
00033 #include "VolMapCreate.h"
00034 #include "QuickSurf.h"
00035 #include <math.h>
00036 #include "MDFF.h"
00037 #include "Voltool.h"
00038 #include <stdio.h>
00039 typedef struct{
00040 double mapA_sum;
00041 double mapB_sum;
00042 double mapA_ss;
00043 double mapB_ss;
00044 double cc;
00045 int size;
00046 const VolumetricData *targetVol;
00047 float *volmap;
00048 const int *numvoxels;
00049 VolumetricData *qsVol;
00050 VolumetricData *newvol;
00051 double threshold;
00052 wkf_mutex_t mtx;
00053 } ccparms;
00054
00055 static void * correlationthread(void *voidparms) {
00056 wkf_tasktile_t tile;
00057 ccparms *parms = NULL;
00058 wkf_threadlaunch_getdata(voidparms, (void **) &parms);
00059 double lmapA_sum = 0.0f;
00060 double lmapB_sum = 0.0f;
00061 double lmapA_ss = 0.0f;
00062 double lmapB_ss = 0.0f;
00063 double lcc = 0.0f;
00064 int lsize = 0;
00065 while (wkf_threadlaunch_next_tile(voidparms, 16384, &tile) != WKF_SCHED_DONE) {
00066 int x;
00067 for (x=tile.start; x<tile.end; x++) {
00068 float ix,iy,iz;
00069 voxel_coord(x, ix, iy, iz, parms->newvol);
00070 float voxelA = parms->qsVol->voxel_value_interpolate_from_coord(ix,iy,iz);
00071 float voxelB = parms->targetVol->voxel_value_interpolate_from_coord(ix,iy,iz);
00072
00073 if (!myisnan(voxelB) && !myisnan(voxelA)) {
00074
00075
00076
00077 if (voxelA >= parms->threshold) {
00078 lmapA_sum += voxelA;
00079 lmapB_sum += voxelB;
00080 lmapA_ss += voxelA*voxelA;
00081 lmapB_ss += voxelB*voxelB;
00082 lcc += voxelA*voxelB;
00083 lsize++;
00084 }
00085 }
00086 }
00087 }
00088
00089 wkf_mutex_lock(&parms->mtx);
00090 parms->mapA_sum += lmapA_sum;
00091 parms->mapB_sum += lmapB_sum;
00092 parms->mapA_ss += lmapA_ss;
00093 parms->mapB_ss += lmapB_ss;
00094 parms->cc += lcc;
00095 parms->size += lsize;
00096 wkf_mutex_unlock(&parms->mtx);
00097
00098 return NULL;
00099 }
00100
00101
00102 int cc_threaded(VolumetricData *qsVol, const VolumetricData *targetVol, double *cc, double threshold) {
00103 ccparms parms;
00104 memset(&parms, 0, sizeof(parms));
00105 parms.mapA_sum = 0;
00106 parms.mapB_sum = 0;
00107 parms.mapA_ss = 0;
00108 parms.mapB_ss = 0;
00109 parms.cc = 0;
00110 parms.size = 0;
00111 parms.volmap = qsVol->data;
00112 int numvoxels [] = {qsVol->xsize, qsVol->ysize, qsVol->zsize};
00113 parms.numvoxels = numvoxels;
00114 parms.targetVol = targetVol;
00115 parms.qsVol = qsVol;
00116 parms.threshold = threshold;
00117
00118 int physprocs = wkf_thread_numprocessors();
00119 int maxprocs = physprocs;
00120
00121
00122
00123 double origin[3] = {0., 0., 0.};
00124 double xaxis[3] = {0., 0., 0.};
00125 double yaxis[3] = {0., 0., 0.};
00126 double zaxis[3] = {0., 0., 0.};
00127 int numvoxelstmp [3] = {0, 0, 0};
00128 float *data = NULL;
00129 VolumetricData *newvol = new VolumetricData("density map", origin, xaxis, yaxis, zaxis,
00130 numvoxelstmp[0], numvoxelstmp[1], numvoxelstmp[2],
00131 data);
00132 init_from_intersection(qsVol, targetVol, newvol);
00133 parms.newvol = newvol;
00134 long volsz = newvol->xsize*newvol->ysize*newvol->zsize;
00135 int numprocs = maxprocs;
00136 wkf_mutex_init(&parms.mtx);
00137 wkf_tasktile_t tile;
00138 tile.start = 0;
00139 tile.end = volsz;
00140 wkf_threadlaunch(numprocs, &parms, correlationthread, &tile);
00141 wkf_mutex_destroy(&parms.mtx);
00142
00143 int size = parms.size;
00144 double aMean = parms.mapA_sum/size;
00145 double bMean = parms.mapB_sum/size;
00146 double stdA = sqrt(parms.mapA_ss/size - aMean*aMean);
00147 double stdB = sqrt(parms.mapB_ss/size - bMean*bMean);
00148
00149 *cc = ((parms.cc) - size*aMean*bMean)/(size * stdA * stdB);
00150 return 0;
00151 }
00152
00153
00154