DGtal  1.5.beta
testNeighborhoodConfigurations.cpp File Reference
#include "DGtalCatch.h"
#include "DGtal/helpers/StdDefs.h"
#include "DGtal/shapes/Shapes.h"
#include "DGtal/base/Common.h"
#include "DGtal/topology/NeighborhoodConfigurations.h"
#include "DGtal/topology/tables/NeighborhoodTables.h"
Include dependency graph for testNeighborhoodConfigurations.cpp:

Go to the source code of this file.

Functions

template<typename TObject >
TObject Object3D (const typename TObject::DigitalTopology &dt)
 
 TEST_CASE ("Check that each neighborhood point in 3D (26 points) has associated a bit in an unsigned integer (NeighborhoodConfiguration).", "[map][mask][3D]")
 
 SCENARIO ("Simplicity tables match on-the-fly calculations for all 3D topologies", "[simple][object][diamond][3D]")
 
 TEST_CASE ("Check that each neighborhood point in 2D (8 points) has associated a bit in an unsigned integer (NeighborhoodConfiguration).", "[map][mask][2D]")
 
 TEST_CASE_METHOD (Objects2D, "Simplicity tables match on-the-fly calculations for all 2D topologies", "[simple][object][balls][2D]")
 
 SCENARIO ("Load isthmus tables", "[isthmus]")
 

Detailed Description

This program is free software: you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.

This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.

You should have received a copy of the GNU General Public License along with this program. If not, see http://www.gnu.org/licenses/.

Author
Pablo Hernandez-Cerdan. Institute of Fundamental Sciences. Massey University. Palmerston North, New Zealand
Date
2018/01/01

Testing classs of NeighborhoodConfigurations

See also
NeighborhoodConfigurations.h

This file is part of the DGtal library.

Definition in file testNeighborhoodConfigurations.cpp.

Function Documentation

◆ Object3D()

template<typename TObject >
TObject Object3D ( const typename TObject::DigitalTopology &  dt)

Definition at line 45 of file testNeighborhoodConfigurations.cpp.

46 {
47  using namespace DGtal;
48  using namespace Z3i;
49  Point p1( -10, -10, -10 );
50  Point p2( 10, 10, 10 );
51  Domain domain( p1, p2 );
52  Point c( 0, 0, 0 );
53  Point r( 3, 0, 0 );
54  DigitalSet diamond_set( domain );
55  for ( auto it = domain.begin(); it != domain.end(); ++it )
56  {
57  if ( (*it - c ).norm1() <= 3 ) diamond_set.insertNew( *it );
58  }
59  diamond_set.erase( c );
60  KSpace K;
62  domain.upperBound(), true);
63 
64  return TObject(dt, diamond_set);
65 }
Aim: A wrapper class around a STL associative container for storing sets of digital points within som...
const ConstIterator & end() const
const ConstIterator & begin() const
const Point & lowerBound() const
const Point & upperBound() const
Aim: This class is a model of CCellularGridSpaceND. It represents the cubical grid as a cell complex,...
bool init(const Point &lower, const Point &upper, bool isClosed)
Specifies the upper and lower bounds for the maximal cells in this space.
DGtal is the top-level namespace which contains all DGtal functions and types.
MyPointD Point
Definition: testClone2.cpp:383
KSpace K
Domain domain

References DGtal::HyperRectDomain< TSpace >::begin(), domain, dt, DGtal::HyperRectDomain< TSpace >::end(), DGtal::DigitalSetByAssociativeContainer< TDomain, TContainer >::erase(), DGtal::KhalimskySpaceND< dim, TInteger >::init(), DGtal::DigitalSetByAssociativeContainer< TDomain, TContainer >::insertNew(), K, DGtal::HyperRectDomain< TSpace >::lowerBound(), and DGtal::HyperRectDomain< TSpace >::upperBound().

◆ SCENARIO() [1/2]

SCENARIO ( "Load isthmus tables"  ,
""  [isthmus] 
)

Definition at line 301 of file testNeighborhoodConfigurations.cpp.

301  {
302  SECTION("isthmus"){
303  const auto & filename = isthmusicity::tableIsthmus;
304  auto ptable = loadTable(filename);
305  const auto & table = *ptable;
306  boost::ignore_unused_variable_warning(table);
307  }
308  SECTION("oneIsthmus"){
309  const auto & filename = isthmusicity::tableOneIsthmus;
310  auto ptable = loadTable(filename);
311  const auto & table = *ptable;
312  boost::ignore_unused_variable_warning(table);
313  }
314  SECTION("twoIsthmus"){
315  const auto & filename = isthmusicity::tableTwoIsthmus;
316  auto ptable = loadTable(filename);
317  const auto & table = *ptable;
318  boost::ignore_unused_variable_warning(table);
319  }
320 }
DGtal::CountedPtr< boost::dynamic_bitset<> > loadTable(const std::string &input_filename, const unsigned int known_size, const bool compressed=true)
SECTION("Testing constant forward iterators")

References DGtal::functions::loadTable(), and SECTION().

◆ SCENARIO() [2/2]

SCENARIO ( "Simplicity tables match on-the-fly calculations for all 3D topologies"  ,
""  [simple][object][diamond][3D] 
)

Definition at line 103 of file testNeighborhoodConfigurations.cpp.

104 {
105  auto mapZeroNeighborhoodToMask = mapZeroPointNeighborhoodToConfigurationMask<Z3i::Point>();
106  using namespace Z3i;
107 
108  SECTION("26_6 topology using loadTable from string and default table size (2^26)"){
109  auto obj = Object3D<Object26_6>(dt26_6);
110  const auto & filename = simplicity::tableSimple26_6;
111  auto ptable = loadTable( filename );
112  CHECK(ptable->size() == 67108864);
113  const auto & table = *ptable;
114  auto & objSet = obj.pointSet();
115  size_t nsimples{0};
116  size_t nsimples_tables{0};
117  for( const auto & p : objSet){
118  auto simple = obj.isSimple(p);
119  if( simple ) ++nsimples;
120  auto cfg = obj.getNeighborhoodConfigurationOccupancy(p, *mapZeroNeighborhoodToMask);
121  auto simple_from_table = table[cfg];
122  if( simple_from_table ) ++nsimples_tables;
123  INFO("Point: " << p << " cfg: " << cfg);
124  CHECK(simple == simple_from_table);
125  }
126  CHECK(nsimples == nsimples_tables);
127  auto border_size = obj.border().size();
128  CHECK(nsimples == border_size);
129  }
130  SECTION("18_6 topology using load table with explicit size (2^26)"){
131  auto obj = Object3D<Object18_6>(dt18_6);
132  const auto & filename = simplicity::tableSimple18_6;
133  // known_size is 2^26 (default)
134  auto ptable = loadTable(filename, 67108864);
135  const auto & table = *ptable;
136  auto & objSet = obj.pointSet();
137  size_t nsimples{0};
138  size_t nsimples_tables{0};
139  for( const auto & p : objSet){
140  auto simple = obj.isSimple(p);
141  if( simple ) ++nsimples;
142  auto cfg = obj.getNeighborhoodConfigurationOccupancy(p, *mapZeroNeighborhoodToMask);
143  auto simple_from_table = table[cfg];
144  if( simple_from_table ) ++nsimples_tables;
145  INFO("Point: " << p << " cfg: " << cfg);
146  CHECK(simple == simple_from_table);
147  }
148  CHECK(nsimples == nsimples_tables);
149  auto border_size = obj.border().size();
150  CHECK(nsimples == border_size);
151  }
152 
153  SECTION("6_26 topology using loadTable with template parameter N=3 (dimension)"){
154  auto obj = Object3D<Object6_26>(dt6_26);
155  const auto & filename = simplicity::tableSimple6_26;
156  auto ptable = loadTable<3>(filename);
157  const auto & table = *ptable;
158  auto & objSet = obj.pointSet();
159  size_t nsimples{0};
160  size_t nsimples_tables{0};
161  for( const auto & p : objSet){
162  auto simple = obj.isSimple(p);
163  if( simple ) ++nsimples;
164  auto cfg = obj.getNeighborhoodConfigurationOccupancy(p, *mapZeroNeighborhoodToMask);
165  auto simple_from_table = table[cfg];
166  if( simple_from_table ) ++nsimples_tables;
167  INFO("Point: " << p << " cfg: " << cfg);
168  CHECK(simple == simple_from_table);
169  }
170  CHECK(nsimples == nsimples_tables);
171 
172  auto border_size = obj.border().size();
173  CHECK(nsimples != border_size);
174  }
175 
176  SECTION("6_18 topology"){
177  auto obj = Object3D<Object6_18>(dt6_18);
178  const auto & filename = simplicity::tableSimple6_18;
179  auto ptable = loadTable(filename);
180  const auto & table = *ptable;
181  auto & objSet = obj.pointSet();
182  size_t nsimples{0};
183  size_t nsimples_tables{0};
184  for( const auto & p : objSet){
185  auto simple = obj.isSimple(p);
186  if( simple ) ++nsimples;
187  auto cfg = obj.getNeighborhoodConfigurationOccupancy(p, *mapZeroNeighborhoodToMask);
188  auto simple_from_table = table[cfg];
189  if( simple_from_table ) ++nsimples_tables;
190  INFO("Point: " << p << " cfg: " << cfg);
191  CHECK(simple == simple_from_table);
192  }
193  CHECK(nsimples == nsimples_tables);
194 
195  auto border_size = obj.border().size();
196  CHECK(nsimples != border_size);
197  }
198 }

References DGtal::functions::loadTable(), and SECTION().

◆ TEST_CASE() [1/2]

TEST_CASE ( "Check that each neighborhood point in 2D (8 points) has associated a bit in an unsigned integer (NeighborhoodConfiguration)."  ,
""  [map][mask][2D] 
)

Definition at line 232 of file testNeighborhoodConfigurations.cpp.

233 {
234  using namespace Z2i;
235  using Map = unordered_map<Point, NeighborhoodConfiguration>;
236  auto pointToMask2D =
237  mapZeroPointNeighborhoodToConfigurationMask< typename Object8_4::Point >();
238  Map truth2D;
239  truth2D[Point{ -1, -1 }] = 1; // 0000 x x 0000 x x 0000 0001
240  truth2D[Point{ 0, -1 }] = 2; // x x x x x x x 0010
241  truth2D[Point{ 1, -1 }] = 4; // x x x x x x x 0100
242  truth2D[Point{ -1, 0 }] = 8; // x x x x x x x 1000
243  truth2D[Point{ 1, 0 }] = 16; // x x x x x x 0001 x
244  truth2D[Point{ -1, 1 }] = 32; // x x x x x x 0010 x
245  truth2D[Point{ 0, 1 }] = 64; // x x x x x x 0100 x
246  truth2D[Point{ 1, 1 }] = 128; // x x x x x x 1000 x
247 
248  CHECK(*pointToMask2D == truth2D);
249 }
std::unordered_map< Cell, CubicalCellData > Map

◆ TEST_CASE() [2/2]

TEST_CASE ( "Check that each neighborhood point in 3D (26 points) has associated a bit in an unsigned integer (NeighborhoodConfiguration)."  ,
""  [map][mask][3D] 
)

Definition at line 67 of file testNeighborhoodConfigurations.cpp.

68 {
69  using namespace Z3i;
70  using Map = unordered_map<Point, NeighborhoodConfiguration>;
71  auto pointToMask3D =
72  mapZeroPointNeighborhoodToConfigurationMask< typename Object26_6::Point >();
73  Map truth3D;
74  truth3D[Point{ -1, -1, -1 }] = 1; // 0000 x x 0000 x x 0000 0001
75  truth3D[Point{ 0, -1, -1 }] = 2; // x x x x x x x 0010
76  truth3D[Point{ 1, -1, -1 }] = 4; // x x x x x x x 0100
77  truth3D[Point{ -1, 0, -1 }] = 8; // x x x x x x x 1000
78  truth3D[Point{ 0, 0, -1 }] = 16; // x x x x x x 0001 x
79  truth3D[Point{ 1, 0, -1 }] = 32; // x x x x x x 0010 x
80  truth3D[Point{ -1, 1, -1 }] = 64; // x x x x x x 0100 x
81  truth3D[Point{ 0, 1, -1 }] = 128; // x x x x x x 1000 x
82  truth3D[Point{ 1, 1, -1 }] = 256; // x x x x x 0001 x x
83  truth3D[Point{ -1, -1, 0 }] = 512; // x x x x x 0010 x x
84  truth3D[Point{ 0, -1, 0 }] = 1024; // x x x x x 0100 x x
85  truth3D[Point{ 1, -1, 0 }] = 2048; // x x x x x 1000 x x
86  truth3D[Point{ -1, 0, 0 }] = 4096; // x x x x 0001 x x x
87  truth3D[Point{ 1, 0, 0 }] = 8192; // x x x x 0010 x x x
88  truth3D[Point{ -1, 1, 0 }] = 16384; // x x x x 0100 x x x
89  truth3D[Point{ 0, 1, 0 }] = 32768; // x x x x 1000 x x x
90  truth3D[Point{ 1, 1, 0 }] = 65536; // x x x 0001 x x x x
91  truth3D[Point{ -1, -1, 1 }] = 131072; // x x x 0010 x x x x
92  truth3D[Point{ 0, -1, 1 }] = 262144; // x x x 0100 x x x x
93  truth3D[Point{ 1, -1, 1 }] = 524288; // x x x 1000 x x x x
94  truth3D[Point{ -1, 0, 1 }] = 1048576; // x x 0001 x x x x x
95  truth3D[Point{ 0, 0, 1 }] = 2097152; // x x 0010 x x x x x
96  truth3D[Point{ 1, 0, 1 }] = 4194304; // x x 0100 x x x x x
97  truth3D[Point{ -1, 1, 1 }] = 8388608; // x x 1000 x x x x x
98  truth3D[Point{ 0, 1, 1 }] = 16777216; // x 0001 x x x x x x
99  truth3D[Point{ 1, 1, 1 }] = 33554432; // x 0010 x x x x x x
100  CHECK(*pointToMask3D == truth3D);
101 
102 }

◆ TEST_CASE_METHOD()

TEST_CASE_METHOD ( Objects2D  ,
"Simplicity tables match on-the-fly calculations for all 2D topologies"  ,
""  [simple][object][balls][2D] 
)

Definition at line 251 of file testNeighborhoodConfigurations.cpp.

252 {
253  auto mapZeroNeighborhoodToMask = mapZeroPointNeighborhoodToConfigurationMask<Z2i::Point>();
254 
255  SECTION("8_4 and 4_8 topologies using loadTable with specific table size (2^8) and with template parameter N=2 (dimension)"){
256  // 8_4
257  {
258  const auto & filename = simplicity::tableSimple8_4;
259  auto ptable = loadTable(filename, 256);
260  const auto & table = *ptable;
261  auto & obj = obj8_4;
262  auto & objSet = obj.pointSet();
263  size_t nsimples{0};
264  size_t nsimples_tables{0};
265  for( const auto & p : objSet){
266  auto simple = obj.isSimple(p);
267  if( simple ) ++nsimples;
268  auto cfg = obj.getNeighborhoodConfigurationOccupancy(p, *mapZeroNeighborhoodToMask);
269  auto simple_from_table = table[cfg];
270  if( simple_from_table ) ++nsimples_tables;
271  INFO("Point: " << p << " cfg: " << cfg);
272  CHECK(simple == simple_from_table);
273  }
274  CHECK(nsimples == nsimples_tables);
275  }
276 
277  // 4_8
278  {
279  const auto & filename = simplicity::tableSimple4_8;
280  auto ptable = loadTable<2>(filename);
281  CHECK(ptable->size() == 256);
282  const auto & table = *ptable;
283  auto & obj = obj4_8;
284  auto & objSet = obj.pointSet();
285  size_t nsimples{0};
286  size_t nsimples_tables{0};
287  for( const auto & p : objSet){
288  auto simple = obj.isSimple(p);
289  if( simple ) ++nsimples;
290  auto cfg = obj.getNeighborhoodConfigurationOccupancy(p, *mapZeroNeighborhoodToMask);
291  auto simple_from_table = table[cfg];
292  if( simple_from_table ) ++nsimples_tables;
293  INFO("Point: " << p << " cfg: " << cfg);
294  CHECK(simple == simple_from_table);
295  }
296  CHECK(nsimples == nsimples_tables);
297  }
298  }
299 }

References DGtal::functions::loadTable(), and SECTION().