[ VIGRA Homepage | Function Index | Class Index | Namespaces | File List | Main Page ]
00001 /************************************************************************/ 00002 /* */ 00003 /* Copyright 2003-2007 by Kasim Terzic, Christian-Dennis Rahn */ 00004 /* and Ullrich Koethe */ 00005 /* Cognitive Systems Group, University of Hamburg, Germany */ 00006 /* */ 00007 /* This file is part of the VIGRA computer vision library. */ 00008 /* The VIGRA Website is */ 00009 /* http://kogs-www.informatik.uni-hamburg.de/~koethe/vigra/ */ 00010 /* Please direct questions, bug reports, and contributions to */ 00011 /* ullrich.koethe@iwr.uni-heidelberg.de or */ 00012 /* vigra@informatik.uni-hamburg.de */ 00013 /* */ 00014 /* Permission is hereby granted, free of charge, to any person */ 00015 /* obtaining a copy of this software and associated documentation */ 00016 /* files (the "Software"), to deal in the Software without */ 00017 /* restriction, including without limitation the rights to use, */ 00018 /* copy, modify, merge, publish, distribute, sublicense, and/or */ 00019 /* sell copies of the Software, and to permit persons to whom the */ 00020 /* Software is furnished to do so, subject to the following */ 00021 /* conditions: */ 00022 /* */ 00023 /* The above copyright notice and this permission notice shall be */ 00024 /* included in all copies or substantial portions of the */ 00025 /* Software. */ 00026 /* */ 00027 /* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND */ 00028 /* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES */ 00029 /* OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND */ 00030 /* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT */ 00031 /* HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, */ 00032 /* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING */ 00033 /* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR */ 00034 /* OTHER DEALINGS IN THE SOFTWARE. */ 00035 /* */ 00036 /************************************************************************/ 00037 00038 #ifndef VIGRA_SEEDEDREGIONGROWING_3D_HXX 00039 #define VIGRA_SEEDEDREGIONGROWING_3D_HXX 00040 00041 #include <vector> 00042 #include <stack> 00043 #include <queue> 00044 #include "utilities.hxx" 00045 #include "stdimage.hxx" 00046 #include "stdimagefunctions.hxx" 00047 #include "seededregiongrowing.hxx" 00048 #include "multi_pointoperators.hxx" 00049 00050 namespace vigra { 00051 00052 namespace detail { 00053 00054 template <class COST, class Diff_type> 00055 class SeedRgVoxel 00056 { 00057 public: 00058 Diff_type location_, nearest_; 00059 COST cost_; 00060 int count_; 00061 int label_; 00062 int dist_; 00063 00064 SeedRgVoxel() 00065 //: location_(0,0,0), nearest_(0,0,0), cost_(0), count_(0), label_(0) 00066 { 00067 location_ = Diff_type(0,0,0); 00068 nearest_ = Diff_type(0,0,0); 00069 cost_ = 0; 00070 count_ = 0; 00071 label_ = 0; 00072 } 00073 00074 SeedRgVoxel(Diff_type const & location, Diff_type const & nearest, 00075 COST const & cost, int const & count, int const & label) 00076 : location_(location), nearest_(nearest), 00077 cost_(cost), count_(count), label_(label) 00078 { 00079 int dx = location_[0] - nearest_[0]; 00080 int dy = location_[1] - nearest_[1]; 00081 int dz = location_[2] - nearest_[2]; 00082 dist_ = dx * dx + dy * dy + dz * dz; 00083 } 00084 00085 void set(Diff_type const & location, Diff_type const & nearest, 00086 COST const & cost, int const & count, int const & label) 00087 { 00088 location_ = location; 00089 nearest_ = nearest; 00090 cost_ = cost; 00091 count_ = count; 00092 label_ = label; 00093 00094 int dx = location_[0] - nearest_[0]; 00095 int dy = location_[1] - nearest_[1]; 00096 int dz = location_[2] - nearest_[2]; 00097 dist_ = dx * dx + dy * dy + dz * dz; 00098 } 00099 00100 struct Compare 00101 { 00102 // must implement > since priority_queue looks for largest element 00103 bool operator()(SeedRgVoxel const & l, 00104 SeedRgVoxel const & r) const 00105 { 00106 if(r.cost_ == l.cost_) 00107 { 00108 if(r.dist_ == l.dist_) return r.count_ < l.count_; 00109 00110 return r.dist_ < l.dist_; 00111 } 00112 00113 return r.cost_ < l.cost_; 00114 } 00115 bool operator()(SeedRgVoxel const * l, 00116 SeedRgVoxel const * r) const 00117 { 00118 if(r->cost_ == l->cost_) 00119 { 00120 if(r->dist_ == l->dist_) return r->count_ < l->count_; 00121 00122 return r->dist_ < l->dist_; 00123 } 00124 00125 return r->cost_ < l->cost_; 00126 } 00127 }; 00128 00129 struct Allocator 00130 { 00131 ~Allocator() 00132 { 00133 while(!freelist_.empty()) 00134 { 00135 delete freelist_.top(); 00136 freelist_.pop(); 00137 } 00138 } 00139 00140 SeedRgVoxel * create(Diff_type const & location, Diff_type const & nearest, 00141 COST const & cost, int const & count, int const & label) 00142 { 00143 if(!freelist_.empty()) 00144 { 00145 SeedRgVoxel * res = freelist_.top(); 00146 freelist_.pop(); 00147 res->set(location, nearest, cost, count, label); 00148 return res; 00149 } 00150 00151 return new SeedRgVoxel(location, nearest, cost, count, label); 00152 } 00153 00154 void dismiss(SeedRgVoxel * p) 00155 { 00156 freelist_.push(p); 00157 } 00158 00159 std::stack<SeedRgVoxel<COST,Diff_type> *> freelist_; 00160 }; 00161 }; 00162 00163 } // namespace detail 00164 00165 /** \addtogroup SeededRegionGrowing 00166 Region segmentation and voronoi tesselation 00167 */ 00168 //@{ 00169 00170 /********************************************************/ 00171 /* */ 00172 /* seededRegionGrowing3D */ 00173 /* */ 00174 /********************************************************/ 00175 00176 /** \brief Three-dimensional Region Segmentation by means of Seeded Region Growing. 00177 00178 This algorithm implements seeded region growing as described in 00179 00180 The seed image is a partly segmented multi-dimensional array which contains uniquely 00181 labeled regions (the seeds) and unlabeled voxels (the candidates, label 0). 00182 Seed regions can be as large as you wish and as small as one voxel. If 00183 there are no candidates, the algorithm will simply copy the seed array 00184 into the output array. Otherwise it will aggregate the candidates into 00185 the existing regions so that a cost function is minimized. This 00186 works as follows: 00187 00188 <ol> 00189 00190 <li> Find all candidate pixels that are 6-adjacent to a seed region. 00191 Calculate the cost for aggregating each candidate into its adajacent region 00192 and put the candidates into a priority queue. 00193 00194 <li> While( priority queue is not empty) 00195 00196 <ol> 00197 00198 <li> Take the candidate with least cost from the queue. If it has not 00199 already been merged, merge it with it's adjacent region. 00200 00201 <li> Put all candidates that are 4-adjacent to the pixel just processed 00202 into the priority queue. 00203 00204 </ol> 00205 00206 </ol> 00207 00208 If <tt>SRGType == CompleteGrow</tt> (the default), this algorithm will 00209 produce a complete 6-connected tesselation of the array. 00210 Other grow types (such as keeping contours for watersheds) are currently not 00211 supported 00212 00213 The cost is determined jointly by the source array and the 00214 region statistics functor. The source array contains feature values for each 00215 pixel which will be used by the region statistics functor to calculate and 00216 update statistics for each region and to calculate the cost for each 00217 candidate. The <TT>RegionStatisticsArray</TT> must be compatible to the 00218 \ref ArrayOfRegionStatistics functor and contains an <em> array</em> of 00219 statistics objects for each region. The indices must correspond to the 00220 labels of the seed regions. The statistics for the initial regions must have 00221 been calculated prior to calling <TT>seededRegionGrowing3D()</TT> 00222 00223 For each candidate 00224 <TT>x</TT> that is adjacent to region <TT>i</TT>, the algorithm will call 00225 <TT>stats[i].cost(as(x))</TT> to get the cost (where <TT>x</TT> is a <TT>SrcImageIterator</TT> 00226 and <TT>as</TT> is 00227 the SrcAccessor). When a candidate has been merged with a region, the 00228 statistics are updated by calling <TT>stats[i].operator()(as(x))</TT>. Since 00229 the <TT>RegionStatisticsArray</TT> is passed by reference, this will overwrite 00230 the original statistics. 00231 00232 If a candidate could be merged into more than one regions with identical 00233 cost, the algorithm will favour the nearest region. If, at any point in the algorithm, 00234 the cost of the current candidate exceeds the optional <tt>max_cost</tt> value (which defaults to 00235 <tt>-1</tt>), region growing is aborted, and all voxels not yet assigned to a region 00236 remain unlabeled. 00237 00238 In some cases, the cost only depends on the feature value of the current 00239 voxel. Then the update operation will simply be a no-op, and the <TT>cost()</TT> 00240 function returns its argument. This behavior is implemented by the 00241 \ref SeedRgDirectValueFunctor. 00242 00243 <b> Declarations:</b> 00244 00245 pass arguments explicitly: 00246 \code 00247 namespace vigra { 00248 template <class SrcImageIterator, class Diff_type, class SrcAccessor, 00249 class SeedImageIterator, class SeedAccessor, 00250 class DestImageIterator, class DestAccessor, 00251 class RegionStatisticsArray, class CostThresholdType > 00252 void seededRegionGrowing3D(SrcImageIterator srcul, Diff_type shape, 00253 SrcAccessor as, 00254 SeedImageIterator seedsul, SeedAccessor aseeds, 00255 DestImageIterator destul, DestAccessor ad, 00256 RegionStatisticsArray & stats, 00257 CostThresholdType max_cost = -1.0, 00258 const SRGType srgType == CompleteGrow); 00259 00260 template <class SrcImageIterator, class Diff_type, class SrcAccessor, 00261 class SeedImageIterator, class SeedAccessor, 00262 class DestImageIterator, class DestAccessor, 00263 class RegionStatisticsArray> 00264 void seededRegionGrowing3D(SrcImageIterator srcul, Diff_type shape, 00265 SrcAccessor as, 00266 SeedImageIterator seedsul, SeedAccessor aseeds, 00267 DestImageIterator destul, DestAccessor ad, 00268 RegionStatisticsArray & stats, 00269 const SRGType srgType == CompleteGrow); 00270 00271 } 00272 \endcode 00273 00274 use argument objects in conjunction with \ref ArgumentObjectFactories : 00275 \code 00276 namespace vigra { 00277 template <class SrcImageIterator, class Shape, class SrcAccessor, 00278 class SeedImageIterator, class SeedAccessor, 00279 class DestImageIterator, class DestAccessor, 00280 class RegionStatisticsArray, class CostThresholdType> 00281 void 00282 seededRegionGrowing3D(triple<SrcImageIterator, Shape, SrcAccessor> img1, 00283 pair<SeedImageIterator, SeedAccessor> img3, 00284 pair<DestImageIterator, DestAccessor> img4, 00285 RegionStatisticsArray & stats, 00286 CostThresholdType max_cost = -1.0, 00287 const SRGType srgType == CompleteGrow); 00288 00289 template <class SrcImageIterator, class Shape, class SrcAccessor, 00290 class SeedImageIterator, class SeedAccessor, 00291 class DestImageIterator, class DestAccessor, 00292 class RegionStatisticsArray> 00293 void 00294 seededRegionGrowing3D(triple<SrcImageIterator, Shape, SrcAccessor> img1, 00295 pair<SeedImageIterator, SeedAccessor> img3, 00296 pair<DestImageIterator, DestAccessor> img4, 00297 RegionStatisticsArray & stats, 00298 const SRGType srgType == CompleteGrow); 00299 } 00300 \endcode 00301 00302 */ 00303 doxygen_overloaded_function(template <...> void seededRegionGrowing3D) 00304 00305 template <class SrcImageIterator, class Diff_type, class SrcAccessor, 00306 class SeedImageIterator, class SeedAccessor, 00307 class DestImageIterator, class DestAccessor, 00308 class RegionStatisticsArray, class CostThresholdType> 00309 void seededRegionGrowing3D(SrcImageIterator srcul, Diff_type shape, 00310 SrcAccessor as, 00311 SeedImageIterator seedsul, SeedAccessor aseeds, 00312 DestImageIterator destul, DestAccessor ad, 00313 RegionStatisticsArray & stats, CostThresholdType max_cost, 00314 const SRGType srgType) 00315 { 00316 SrcImageIterator srclr = srcul + shape; 00317 //int w = srclr.x - srcul.x; 00318 int w = shape[0]; 00319 //int h = srclr.y - srcul.y; 00320 int h = shape[1]; 00321 //int d = srclr.z - srcul.z; 00322 int d = shape[2]; 00323 int count = 0; 00324 00325 SrcImageIterator isy = srcul, isx = srcul, isz = srcul; // iterators for the src image 00326 00327 typedef typename RegionStatisticsArray::value_type RegionStatistics; 00328 typedef typename PromoteTraits<typename RegionStatistics::cost_type, CostThresholdType>::Promote CostType; 00329 typedef detail::SeedRgVoxel<CostType, Diff_type> Voxel; 00330 00331 typename Voxel::Allocator allocator; 00332 00333 typedef std::priority_queue< Voxel *, 00334 std::vector<Voxel *>, 00335 typename Voxel::Compare > SeedRgVoxelHeap; 00336 typedef MultiArray<3, int> IVolume; 00337 00338 // copy seed image in an image with border 00339 Diff_type regionshape = shape + Diff_type(2,2,2); 00340 IVolume regions(regionshape); 00341 MultiIterator<3,int> ir = regions.traverser_begin(); 00342 ir = ir + Diff_type(1,1,1); 00343 00344 //IVolume::Iterator iry, irx, irz; 00345 MultiIterator<3,int> iry, irx, irz; 00346 00347 //initImageBorder(destImageRange(regions), 1, SRGWatershedLabel); 00348 initMultiArrayBorder(destMultiArrayRange(regions), 1, SRGWatershedLabel); 00349 00350 copyMultiArray(seedsul, Diff_type(w,h,d), aseeds, ir, AccessorTraits<int>::default_accessor()/* vigra::StandardValueAccessor<int>*/); 00351 00352 // allocate and init memory for the results 00353 00354 SeedRgVoxelHeap pheap; 00355 int cneighbor; 00356 00357 static const Diff_type dist[] = { Diff_type(-1, 0, 0), Diff_type( 0,-1, 0), 00358 Diff_type( 1, 0, 0), Diff_type( 0, 1, 0), 00359 Diff_type( 0, 0,-1), Diff_type( 0, 0, 1) }; 00360 00361 Diff_type pos(0,0,0); 00362 00363 for(isz=srcul, irz=ir, pos[2]=0; pos[2]<d; 00364 pos[2]++, isz.dim2()++, irz.dim2()++) 00365 { 00366 //std::cerr << "Z = " << pos[2] << std::endl; 00367 00368 for(isy=isz, iry=irz, pos[1]=0; pos[1]<h; 00369 pos[1]++, isy.dim1()++, iry.dim1()++) 00370 { 00371 //std::cerr << "Y = " << pos[1] << std::endl; 00372 00373 for(isx=isy, irx=iry, pos[0]=0; pos[0]<w; 00374 pos[0]++, isx.dim0()++, irx.dim0()++) 00375 { 00376 //std::cerr << "X = " << pos[0] << std::endl; 00377 00378 if(*irx == 0) 00379 { 00380 // find candidate pixels for growing and fill heap 00381 for(int i=0; i<6; i++) 00382 { 00383 cneighbor = *(irx + dist[i]); 00384 if(cneighbor > 0) 00385 { 00386 CostType cost = stats[cneighbor].cost(as(isx)); 00387 00388 Voxel * voxel = 00389 allocator.create(pos, pos+dist[i], cost, count++, cneighbor); 00390 pheap.push(voxel); 00391 } 00392 } 00393 } 00394 } 00395 } 00396 } 00397 00398 // perform region growing 00399 while(pheap.size() != 0) 00400 { 00401 Voxel * voxel = pheap.top(); 00402 pheap.pop(); 00403 00404 if(max_cost > NumericTraits<CostThresholdType>::zero() && voxel->cost_ > max_cost) break; 00405 00406 Diff_type pos = voxel->location_; 00407 Diff_type nearest = voxel->nearest_; 00408 int lab = voxel->label_; 00409 00410 allocator.dismiss(voxel); 00411 00412 irx = ir + pos; 00413 isx = srcul + pos; 00414 00415 if(*irx) // already labelled region / watershed? 00416 continue; 00417 00418 if(srgType == KeepContours) 00419 { 00420 for(int i=0; i<6; i++) 00421 { 00422 cneighbor = * (irx + dist[i]); 00423 if((cneighbor>0) && (cneighbor != lab)) 00424 { 00425 lab = SRGWatershedLabel; 00426 break; 00427 } 00428 } 00429 } 00430 00431 *irx = lab; 00432 00433 if((srgType != KeepContours) || (lab > 0)) 00434 { 00435 // update statistics 00436 stats[*irx](as(isx)); 00437 00438 // search neighborhood 00439 // second pass: find new candidate pixels 00440 for(int i=0; i<6; i++) 00441 { 00442 if(*(irx + dist[i]) == 0) 00443 { 00444 CostType cost = stats[lab].cost(as(isx, dist[i])); 00445 00446 Voxel * new_voxel = 00447 allocator.create(pos+dist[i], nearest, cost, count++, lab); 00448 pheap.push(new_voxel); 00449 } 00450 } 00451 } 00452 } 00453 00454 // write result 00455 transformMultiArray(ir, Diff_type(w,h,d), AccessorTraits<int>::default_accessor()/* regions.accessor()*/, destul, ad, 00456 detail::UnlabelWatersheds()); 00457 } 00458 /* 00459 template <class SrcImageIterator, class SrcAccessor, 00460 class SeedImageIterator, class SeedAccessor, 00461 class DestImageIterator, class DestAccessor, 00462 class RegionStatisticsArray> 00463 inline void 00464 seededRegionGrowing3D(SrcImageIterator srcul, 00465 SrcImageIterator srclr, SrcAccessor as, 00466 SeedImageIterator seedsul, SeedAccessor aseeds, 00467 DestImageIterator destul, DestAccessor ad, 00468 RegionStatisticsArray & stats) 00469 { 00470 seededRegionGrowing3D(srcul, srclr, as, 00471 seedsul, aseeds, 00472 destul, ad, 00473 stats, CompleteGrow); 00474 }*/ 00475 /* 00476 template <class SrcImageIterator, class SrcAccessor, 00477 class SeedImageIterator, class SeedAccessor, 00478 class DestImageIterator, class DestAccessor, 00479 class RegionStatisticsArray> 00480 inline void 00481 seededRegionGrowing3D(triple<SrcImageIterator, SrcImageIterator, SrcAccessor> img1, 00482 pair<SeedImageIterator, SeedAccessor> img3, 00483 pair<DestImageIterator, DestAccessor> img4, 00484 RegionStatisticsArray & stats, 00485 SRGType srgType) 00486 { 00487 seededRegionGrowing3D(img1.first, img1.second, img1.third, 00488 img3.first, img3.second, 00489 img4.first, img4.second, 00490 stats, srgType); 00491 } 00492 00493 template <class SrcImageIterator, class SrcAccessor, 00494 class SeedImageIterator, class SeedAccessor, 00495 class DestImageIterator, class DestAccessor, 00496 class RegionStatisticsArray> 00497 inline void 00498 seededRegionGrowing3D(triple<SrcImageIterator, SrcImageIterator, SrcAccessor> img1, 00499 pair<SeedImageIterator, SeedAccessor> img3, 00500 pair<DestImageIterator, DestAccessor> img4, 00501 RegionStatisticsArray & stats) 00502 { 00503 seededRegionGrowing3D(img1.first, img1.second, img1.third, 00504 img3.first, img3.second, 00505 img4.first, img4.second, 00506 stats, CompleteGrow); 00507 } 00508 */ 00509 00510 template <class SrcImageIterator, class Diff_type, class SrcAccessor, 00511 class SeedImageIterator, class SeedAccessor, 00512 class DestImageIterator, class DestAccessor, 00513 class RegionStatisticsArray, class CostThresholdType> 00514 void seededRegionGrowing3D(SrcImageIterator srcul, Diff_type shape, 00515 SrcAccessor as, 00516 SeedImageIterator seedsul, SeedAccessor aseeds, 00517 DestImageIterator destul, DestAccessor ad, 00518 RegionStatisticsArray & stats, CostThresholdType max_cost) 00519 { 00520 seededRegionGrowing3D( srcul, shape, as, seedsul, aseeds, destul, ad, stats, max_cost, CompleteGrow); 00521 } 00522 00523 template <class SrcImageIterator, class Diff_type, class SrcAccessor, 00524 class SeedImageIterator, class SeedAccessor, 00525 class DestImageIterator, class DestAccessor, 00526 class RegionStatisticsArray > 00527 void seededRegionGrowing3D(SrcImageIterator srcul, Diff_type shape, 00528 SrcAccessor as, 00529 SeedImageIterator seedsul, SeedAccessor aseeds, 00530 DestImageIterator destul, DestAccessor ad, 00531 RegionStatisticsArray & stats) 00532 { 00533 seededRegionGrowing3D( srcul, shape, as, seedsul, aseeds, destul, ad, stats, -1.0, CompleteGrow); 00534 } 00535 00536 template <class SrcImageIterator, class Diff_type, class SrcAccessor, 00537 class SeedImageIterator, class SeedAccessor, 00538 class DestImageIterator, class DestAccessor, 00539 class RegionStatisticsArray > 00540 void seededRegionGrowing3D(SrcImageIterator srcul, Diff_type shape, 00541 SrcAccessor as, 00542 SeedImageIterator seedsul, SeedAccessor aseeds, 00543 DestImageIterator destul, DestAccessor ad, 00544 RegionStatisticsArray & stats, SRGType srgType) 00545 { 00546 seededRegionGrowing3D( srcul, shape, as, seedsul, aseeds, destul, ad, stats, -1.0, srgType); 00547 } 00548 00549 00550 00551 template <class SrcImageIterator, class Shape, class SrcAccessor, 00552 class SeedImageIterator, class SeedAccessor, 00553 class DestImageIterator, class DestAccessor, 00554 class RegionStatisticsArray> 00555 inline void 00556 seededRegionGrowing3D(triple<SrcImageIterator, Shape, SrcAccessor> img1, 00557 pair<SeedImageIterator, SeedAccessor> img3, 00558 pair<DestImageIterator, DestAccessor> img4, 00559 RegionStatisticsArray & stats, int max_cost) 00560 { 00561 seededRegionGrowing3D(img1.first, img1.second, img1.third, 00562 img3.first, img3.second, 00563 img4.first, img4.second, 00564 stats, max_cost, CompleteGrow); 00565 } 00566 00567 template <class SrcImageIterator, class Shape, class SrcAccessor, 00568 class SeedImageIterator, class SeedAccessor, 00569 class DestImageIterator, class DestAccessor, 00570 class RegionStatisticsArray, class CostThresholdType> 00571 inline void 00572 seededRegionGrowing3D(triple<SrcImageIterator, Shape, SrcAccessor> img1, 00573 pair<SeedImageIterator, SeedAccessor> img3, 00574 pair<DestImageIterator, DestAccessor> img4, 00575 RegionStatisticsArray & stats, CostThresholdType max_cost, const SRGType srgType) 00576 { 00577 seededRegionGrowing3D(img1.first, img1.second, img1.third, 00578 img3.first, img3.second, 00579 img4.first, img4.second, 00580 stats, max_cost, srgType); 00581 } 00582 00583 00584 template <class SrcImageIterator, class Shape, class SrcAccessor, 00585 class SeedImageIterator, class SeedAccessor, 00586 class DestImageIterator, class DestAccessor, 00587 class RegionStatisticsArray> 00588 inline void 00589 seededRegionGrowing3D(triple<SrcImageIterator, Shape, SrcAccessor> img1, 00590 pair<SeedImageIterator, SeedAccessor> img3, 00591 pair<DestImageIterator, DestAccessor> img4, 00592 RegionStatisticsArray & stats, const SRGType srgType) 00593 { 00594 seededRegionGrowing3D(img1.first, img1.second, img1.third, 00595 img3.first, img3.second, 00596 img4.first, img4.second, 00597 stats, -1.0, srgType); 00598 } 00599 00600 template <class SrcImageIterator, class Shape, class SrcAccessor, 00601 class SeedImageIterator, class SeedAccessor, 00602 class DestImageIterator, class DestAccessor, 00603 class RegionStatisticsArray> 00604 inline void 00605 seededRegionGrowing3D(triple<SrcImageIterator, Shape, SrcAccessor> img1, 00606 pair<SeedImageIterator, SeedAccessor> img3, 00607 pair<DestImageIterator, DestAccessor> img4, 00608 RegionStatisticsArray & stats) 00609 { 00610 seededRegionGrowing3D(img1.first, img1.second, img1.third, 00611 img3.first, img3.second, 00612 img4.first, img4.second, 00613 stats, -1.0, CompleteGrow); 00614 } 00615 00616 00617 00618 } // namespace vigra 00619 00620 #endif // VIGRA_SEEDEDREGIONGROWING_HXX 00621
© Ullrich Köthe (ullrich.koethe@iwr.uni-heidelberg.de) |
html generated using doxygen and Python
|