37 #ifndef VIGRA_SEEDEDREGIONGROWING_3D_HXX 
   38 #define VIGRA_SEEDEDREGIONGROWING_3D_HXX 
   44 #include "stdimage.hxx" 
   45 #include "stdimagefunctions.hxx" 
   46 #include "seededregiongrowing.hxx" 
   47 #include "multi_shape.hxx" 
   48 #include "multi_pointoperators.hxx" 
   49 #include "voxelneighborhood.hxx" 
   55 template <
class COST, 
class Diff_type>
 
   59     Diff_type location_, nearest_;
 
   68         location_ = Diff_type(0,0,0);
 
   69         nearest_ = Diff_type(0,0,0);
 
   75     SeedRgVoxel(Diff_type 
const & location, Diff_type 
const & nearest,
 
   76                 COST 
const & cost, 
int const & count, 
int const & label)
 
   77     : location_(location), nearest_(nearest),
 
   78       cost_(cost), count_(count), label_(label)
 
   80         int dx = location_[0] - nearest_[0];
 
   81         int dy = location_[1] - nearest_[1];
 
   82         int dz = location_[2] - nearest_[2];
 
   83         dist_ = dx * dx + dy * dy + dz * dz;
 
   86     void set(Diff_type 
const & location, Diff_type 
const & nearest,
 
   87              COST 
const & cost, 
int const & count, 
int const & label)
 
   95         int dx = location_[0] - nearest_[0];
 
   96         int dy = location_[1] - nearest_[1];
 
   97         int dz = location_[2] - nearest_[2];
 
   98         dist_ = dx * dx + dy * dy + dz * dz;
 
  104         bool operator()(SeedRgVoxel 
const & l,
 
  105                         SeedRgVoxel 
const & r)
 const 
  107             if(r.cost_ == l.cost_)
 
  109                 if(r.dist_ == l.dist_) 
return r.count_ < l.count_;
 
  111                 return r.dist_ < l.dist_;
 
  114             return r.cost_ < l.cost_;
 
  116         bool operator()(SeedRgVoxel 
const * l,
 
  117                         SeedRgVoxel 
const * r)
 const 
  119             if(r->cost_ == l->cost_)
 
  121                 if(r->dist_ == l->dist_) 
return r->count_ < l->count_;
 
  123                 return r->dist_ < l->dist_;
 
  126             return r->cost_ < l->cost_;
 
  134             while(!freelist_.empty())
 
  136                 delete freelist_.top();
 
  141         SeedRgVoxel * create(Diff_type 
const & location, Diff_type 
const & nearest,
 
  142                              COST 
const & cost, 
int const & count, 
int const & label)
 
  144             if(!freelist_.empty())
 
  146                 SeedRgVoxel * res = freelist_.top();
 
  148                 res->set(location, nearest, cost, count, label);
 
  152             return new SeedRgVoxel(location, nearest, cost, count, label);
 
  155         void dismiss(SeedRgVoxel * p)
 
  160         std::stack<SeedRgVoxel<COST,Diff_type> *> freelist_;
 
  318 template <
class SrcImageIterator, 
class Diff_type, 
class SrcAccessor,
 
  319           class SeedImageIterator, 
class SeedAccessor,
 
  320           class DestImageIterator, 
class DestAccessor,
 
  321           class RegionStatisticsArray, 
class Neighborhood>
 
  324                       SeedImageIterator seedsul, SeedAccessor aseeds,
 
  325                       DestImageIterator destul, DestAccessor ad,
 
  326                       RegionStatisticsArray & stats,
 
  340     SrcImageIterator isy = srcul, isx = srcul, isz = srcul;  
 
  342     typedef typename RegionStatisticsArray::value_type RegionStatistics;
 
  343     typedef typename PromoteTraits<typename RegionStatistics::cost_type, double>::Promote CostType;
 
  344     typedef detail::SeedRgVoxel<CostType, Diff_type> Voxel;
 
  346     typename Voxel::Allocator allocator;
 
  348     typedef std::priority_queue< Voxel *,
 
  349                                  std::vector<Voxel *>,
 
  350                                  typename Voxel::Compare >  SeedRgVoxelHeap;
 
  351     typedef MultiArray<3, int> IVolume;
 
  352     typedef IVolume::traverser Traverser;
 
  355     Diff_type regionshape = shape + Diff_type(2,2,2);
 
  356     IVolume regions(regionshape);
 
  357     Traverser ir = regions.traverser_begin();
 
  358     ir = ir + Diff_type(1,1,1);
 
  361    Traverser iry, irx, irz;
 
  366     copyMultiArray(seedsul, Diff_type(w,h,d), aseeds, ir, AccessorTraits<int>::default_accessor());
 
  370     SeedRgVoxelHeap pheap;
 
  373     typedef typename Neighborhood::Direction 
Direction;
 
  374     int directionCount = Neighborhood::DirectionCount;
 
  376     Diff_type pos(0,0,0);
 
  378     for(isz=srcul, irz=ir, pos[2]=0; pos[2]<d;
 
  379             pos[2]++, isz.dim2()++, irz.dim2()++)
 
  383         for(isy=isz, iry=irz, pos[1]=0; pos[1]<h;
 
  384             pos[1]++, isy.dim1()++, iry.dim1()++)
 
  388             for(isx=isy, irx=iry, pos[0]=0; pos[0]<w;
 
  389                 pos[0]++, isx.dim0()++, irx.dim0()++)
 
  396                     for(
int i=0; i<directionCount; i++)
 
  398                         cneighbor = *(irx + Neighborhood::diff((Direction)i));
 
  401                             CostType cost = stats[cneighbor].cost(as(isx));
 
  404                                 allocator.create(pos, pos+Neighborhood::diff((Direction)i), cost, count++, cneighbor);
 
  414     while(pheap.size() != 0)
 
  416         Voxel * voxel = pheap.top();
 
  419         Diff_type pos = voxel->location_;
 
  420         Diff_type nearest = voxel->nearest_;
 
  421         int lab = voxel->label_;
 
  422         CostType cost = voxel->cost_;
 
  424         allocator.dismiss(voxel);
 
  426         if((srgType & StopAtThreshold) != 0 && cost > max_cost)
 
  435         if((srgType & KeepContours) != 0)
 
  437             for(
int i=0; i<directionCount; i++)
 
  439                 cneighbor = * (irx + Neighborhood::diff((Direction)i));
 
  440                 if((cneighbor>0) && (cneighbor != lab))
 
  442                     lab = SRGWatershedLabel;
 
  450         if((srgType & KeepContours) == 0 || lab > 0)
 
  453             stats[*irx](as(isx));
 
  457             for(
int i=0; i<directionCount; i++)
 
  459                 if(*(irx + Neighborhood::diff((Direction)i)) == 0)
 
  461                     CostType cost = stats[lab].cost(as(isx, Neighborhood::diff((Direction)i)));
 
  464                         allocator.create(pos+Neighborhood::diff((Direction)i), nearest, cost, count++, lab);
 
  465                     pheap.push(new_voxel);
 
  472     while(pheap.size() != 0)
 
  474         allocator.dismiss(pheap.top());
 
  480                         destul, ad, detail::UnlabelWatersheds());
 
  483 template <
class SrcImageIterator, 
class Diff_type, 
class SrcAccessor,
 
  484           class SeedImageIterator, 
class SeedAccessor,
 
  485           class DestImageIterator, 
class DestAccessor,
 
  486           class RegionStatisticsArray, 
class Neighborhood >
 
  489                       SeedImageIterator seedsul, SeedAccessor aseeds,
 
  490                       DestImageIterator destul, DestAccessor ad,
 
  491                       RegionStatisticsArray & stats, 
SRGType srgType, Neighborhood n)
 
  494                            destul, ad, stats, srgType, n, NumericTraits<double>::max());
 
  497 template <
class SrcImageIterator, 
class Diff_type, 
class SrcAccessor,
 
  498           class SeedImageIterator, 
class SeedAccessor,
 
  499           class DestImageIterator, 
class DestAccessor,
 
  500           class RegionStatisticsArray >
 
  503                       SeedImageIterator seedsul, SeedAccessor aseeds,
 
  504                       DestImageIterator destul, DestAccessor ad,
 
  505                       RegionStatisticsArray & stats, 
SRGType srgType)
 
  511 template <
class SrcImageIterator, 
class Diff_type, 
class SrcAccessor,
 
  512           class SeedImageIterator, 
class SeedAccessor,
 
  513           class DestImageIterator, 
class DestAccessor,
 
  514           class RegionStatisticsArray >
 
  517                       SeedImageIterator seedsul, SeedAccessor aseeds,
 
  518                       DestImageIterator destul, DestAccessor ad,
 
  519                       RegionStatisticsArray & stats)
 
  522                            stats, CompleteGrow);
 
  525 template <
class SrcImageIterator, 
class Shape, 
class SrcAccessor,
 
  526           class SeedImageIterator, 
class SeedAccessor,
 
  527           class DestImageIterator, 
class DestAccessor,
 
  528           class RegionStatisticsArray, 
class Neighborhood>
 
  531                       pair<SeedImageIterator, SeedAccessor> img3,
 
  532                       pair<DestImageIterator, DestAccessor> img4,
 
  533                       RegionStatisticsArray & stats,
 
  534                       SRGType srgType, Neighborhood n, 
double max_cost)
 
  537                           img3.first, img3.second,
 
  538                           img4.first, img4.second,
 
  539                           stats, srgType, n, max_cost);
 
  542 template <
class SrcImageIterator, 
class Shape, 
class SrcAccessor,
 
  543           class SeedImageIterator, 
class SeedAccessor,
 
  544           class DestImageIterator, 
class DestAccessor,
 
  545           class RegionStatisticsArray, 
class Neighborhood>
 
  548                       pair<SeedImageIterator, SeedAccessor> img3,
 
  549                       pair<DestImageIterator, DestAccessor> img4,
 
  550                       RegionStatisticsArray & stats,
 
  551                       SRGType srgType, Neighborhood n)
 
  554                           img3.first, img3.second,
 
  555                           img4.first, img4.second,
 
  556                           stats, srgType, n, NumericTraits<double>::max());
 
  559 template <
class SrcImageIterator, 
class Shape, 
class SrcAccessor,
 
  560           class SeedImageIterator, 
class SeedAccessor,
 
  561           class DestImageIterator, 
class DestAccessor,
 
  562           class RegionStatisticsArray>
 
  565                       pair<SeedImageIterator, SeedAccessor> img3,
 
  566                       pair<DestImageIterator, DestAccessor> img4,
 
  567                       RegionStatisticsArray & stats, 
SRGType srgType)
 
  570                           img3.first, img3.second,
 
  571                           img4.first, img4.second,
 
  575 template <
class SrcImageIterator, 
class Shape, 
class SrcAccessor,
 
  576           class SeedImageIterator, 
class SeedAccessor,
 
  577           class DestImageIterator, 
class DestAccessor,
 
  578           class RegionStatisticsArray>
 
  581                       pair<SeedImageIterator, SeedAccessor> img3,
 
  582                       pair<DestImageIterator, DestAccessor> img4,
 
  583                       RegionStatisticsArray & stats)
 
  586                           img3.first, img3.second,
 
  587                           img4.first, img4.second,
 
  591 template <
class T1, 
class S1,
 
  594           class RegionStatisticsArray, 
class Neighborhood>
 
  597                       MultiArrayView<3, TS, AS> 
const & img3,
 
  598                       MultiArrayView<3, T2, S2> img4,
 
  599                       RegionStatisticsArray & stats,
 
  600                       SRGType srgType, Neighborhood n, 
double max_cost)
 
  602     vigra_precondition(img1.shape() == img3.shape(),
 
  603         "seededRegionGrowing3D(): shape mismatch between input and output.");
 
  606                           destMultiArray(img4),
 
  607                           stats, srgType, n, max_cost);
 
  610 template <
class T1, 
class S1,
 
  613           class RegionStatisticsArray, 
class Neighborhood>
 
  616                       MultiArrayView<3, TS, AS> 
const & img3,
 
  617                       MultiArrayView<3, T2, S2> img4,
 
  618                       RegionStatisticsArray & stats,
 
  619                       SRGType srgType, Neighborhood n)
 
  621     vigra_precondition(img1.shape() == img3.shape(),
 
  622         "seededRegionGrowing3D(): shape mismatch between input and output.");
 
  625                           destMultiArray(img4),
 
  626                           stats, srgType, n, NumericTraits<double>::max());
 
  629 template <
class T1, 
class S1,
 
  632           class RegionStatisticsArray>
 
  635                       MultiArrayView<3, TS, AS> 
const & img3,
 
  636                       MultiArrayView<3, T2, S2> img4,
 
  637                       RegionStatisticsArray & stats, 
SRGType srgType)
 
  639     vigra_precondition(img1.shape() == img3.shape(),
 
  640         "seededRegionGrowing3D(): shape mismatch between input and output.");
 
  643                           destMultiArray(img4),
 
  647 template <
class T1, 
class S1,
 
  650           class RegionStatisticsArray>
 
  653                       MultiArrayView<3, TS, AS> 
const & img3,
 
  654                       MultiArrayView<3, T2, S2> img4,
 
  655                       RegionStatisticsArray & stats)
 
  657     vigra_precondition(img1.shape() == img3.shape(),
 
  658         "seededRegionGrowing3D(): shape mismatch between input and output.");
 
  661                           destMultiArray(img4),
 
  667 #endif // VIGRA_SEEDEDREGIONGROWING_HXX 
void initMultiArrayBorder(...)
Write values to the specified border values in the array. 
SRGType
Definition: seededregiongrowing.hxx:176
void seededRegionGrowing3D(...)
Three-dimensional Region Segmentation by means of Seeded Region Growing. 
NeighborCode::Direction Direction
Definition: pixelneighborhood.hxx:321
doxygen_overloaded_function(template<...> void separableConvolveBlockwise) template< unsigned int N
Separated convolution on ChunkedArrays. 
void copyMultiArray(...)
Copy a multi-dimensional array. 
Neighborhood3DSix::NeighborCode3D NeighborCode3DSix
Definition: voxelneighborhood.hxx:490
void transformMultiArray(...)
Transform a multi-dimensional array with a unary function or functor.