From c9cdcbf53971c2df32d27beaece523d1706d165a Mon Sep 17 00:00:00 2001 From: James McClure Date: Thu, 22 May 2014 14:43:49 -0400 Subject: [PATCH] Added two functions to assign blob IDs in parallel --- pmmc/AssignBlobID.cpp | 207 +++++++++++++++++++++++++++++++++++++++++- 1 file changed, 206 insertions(+), 1 deletion(-) diff --git a/pmmc/AssignBlobID.cpp b/pmmc/AssignBlobID.cpp index 1227aaff..a53b6658 100644 --- a/pmmc/AssignBlobID.cpp +++ b/pmmc/AssignBlobID.cpp @@ -19,6 +19,212 @@ inline double PhaseAverageScalar(int *PhaseID, double *Scalar, int N, int Np) } } +inline int AssignGlobalBlobID(IntArray &blobs, int &nblobs, int &ncubes, IntArray &indicator, &IntArray cubes_in_blob, int number_of_blobs_below_rank) +{ + // This routine takes the local blob ID and assigns a globally unique tag to each blob + // the local tag is already unique, we just need to add it to the number of blobs determined + // for all ranks < the rank of the processor calling this routine + // Note that the total number of connected blobs is less than number_of_blobs_below_rank + // since the tag that results after calling this routine does not reflect connectivity + // between different MPI sub-domains. + int i,j,k; + int start=0,finish; + int a,c; + + int minimumBlobID; + + for (a=0;avf|S>vs) starting from (i,j,k) - oil blob + // F>vf => oil phase S>vs => in porespace + // update the list of blobs, indicator mesh + int m = F.m; // maxima for the meshes + int n = F.n; + int o = F.o; + + int cubes_in_blob=0; + int nrecent = 1; // number of nodes added at most recent sweep + temp(0,0) = startx; // Set the initial point as a "seed" for the sweeps + temp(1,0) = starty; + temp(2,0) = startz; + int ntotal = 1; // total number of nodes in blob + indicator(startx,starty,startz) = nblobs; + + int p,s,x,y,z,start,finish,nodx,nody,nodz; + int imin=startx,imax=startx,jmin=starty,jmax=starty; // initialize maxima / minima + int kmin=startz,kmax=startz; + int d[26][3] = {{1,0,0},{-1,0,0},{0,1,0},{0,-1,0},{0,0,1},{0,0,-1}, + {1,1,0},{1,-1,0},{-1,1,0},{-1,-1,0},{1,0,1},{-1,0,1}, + {1,0,-1},{-1,0,-1},{0,1,1},{0,-1,1},{0,1,-1},{0,-1,-1}, + {1,1,1},{1,1,-1},{1,-1,1},{1,-1,-1},{-1,1,1},{-1,1,-1}, + {-1,-1,1},{-1,-1,-1}}; // directions to neighbors + int cube[8][3] = {{0,0,0},{1,0,0},{0,1,0},{1,1,0},{0,0,1},{1,0,1},{0,1,1},{1,1,1}}; // cube corners + bool status = 1; // status == true => continue to look for points + while (status == 1){ + start = ntotal - nrecent; + finish = ntotal; + nrecent = 0; // set recent points back to zero for next sweep through + for (s=start;s m-1 ){ nodx = 0; } + nody=y+d[p][1]; + if (nody < 0 ){ nody = n-1; } // Periodic BC for y + if (nody > n-1 ){ nody = 0; } + nodz=z+d[p][2]; + if (nodz < 0 ){ nodz = 0; } // No periodic BC for z + if (nodz > o-1 ){ nodz = o-1; } + if ( F(nodx,nody,nodz) > vf && S(nodx,nody,nodz) > vs + && indicator(nodx,nody,nodz) == -1 ){ + // Node is a part of the blob - add it to the list + temp(0,ntotal) = nodx; + temp(1,ntotal) = nody; + temp(2,ntotal) = nodz; + ntotal++; + nrecent++; + // Update the indicator map + indicator(nodx,nody,nodz) = nblobs; + // Update the min / max for the cube loop + if ( nodx < imin ){ imin = nodx; } + if ( nodx > imax ){ imax = nodx; } + if ( nody < jmin ){ jmin = nody; } + if ( nody > jmax ){ jmax = nody; } + if ( nodz < kmin ){ kmin = nodz; } + if ( nodz > kmax ){ kmax = nodz; } + } + else if (F(nodx,nody,nodz) > vf && S(nodx,nody,nodz) > vs + && indicator(nodx,nody,nodz) > -1 && indicator(nodx,nody,nodz) != nblobs){ + // Some kind of error in algorithm + printf("Error in blob search algorithm!"); + } + } + + } + if ( nrecent == 0){ + status = 0; + } + } + // Use points in temporary storage array to add cubes to the list of blobs + if ( imin > 0) { imin = imin-1; } +// if ( imax < m-1) { imax = imax+1; } + if ( jmin > 0) { jmin = jmin-1; } +// if ( jmax < n-1) { jmax = jmax+1; } + if ( kmin > 0) { kmin = kmin-1; } +// if ( kmax < o-1) { kmax = kmax+1; } + int i,j,k; + bool add; + for (k=kmin;k -1 && indicator(nodx,nody,nodz) != nblobs){ + printf("Overlapping cube!"); + cout << i << ", " << j << ", " << k << endl; + } + } + } + } + } + } + + return cubes_in_blob; +} inline int ComputeBlob(IntArray blobs, int &nblobs, int &ncubes, IntArray indicator, DoubleArray F, DoubleArray S, double vf, double vs, int startx, int starty, @@ -31,7 +237,6 @@ inline int ComputeBlob(IntArray blobs, int &nblobs, int &ncubes, IntArray indica int n = F.n; int o = F.o; - int cubes_in_blob=0; int nrecent = 1; // number of nodes added at most recent sweep temp(0,0) = startx; // Set the initial point as a "seed" for the sweeps