37 #if __GXX_EXPERIMENTAL_CXX0X__ && ( __GNUC__ >= 4 ) && ( __GNUC_MINOR__ >= 6 )
38 #include <forward_list>
40 #include <boost/version.hpp>
41 #include <boost/random/mersenne_twister.hpp>
42 #include <boost/random/uniform_smallint.hpp>
43 #include <boost/random/uniform_01.hpp>
44 #include <boost/random/geometric_distribution.hpp>
45 #include <boost/random/variate_generator.hpp>
48 #include "DGtal/base/Common.h"
49 #include "DGtal/base/LabelledMap.h"
53 #define BOOST_MAJOR_VERSION (BOOST_VERSION / 100000)
54 #define BOOST_MINOR_VERSION (( BOOST_VERSION / 100) % 1000)
55 #define BOOST_SUBMINOR_VERSION (BOOST_VERSION % 100)
58 using namespace DGtal;
75 template <
typename Value>
78 typedef Value ValueType;
89 DynArrayLXY(
unsigned int _L,
unsigned int _X,
unsigned int _Y,
Value invalid )
90 :
L( _L ), X( _X ), Y( _Y )
93 _data =
new Value[
L * X * Y ];
104 for (
unsigned int l = 0; l <
L; ++l )
105 for (
unsigned int x = 0; x < X; ++x )
106 for (
unsigned int y = 0; y < Y; ++y )
107 setValue( _invalid, l, x, y );
111 size_t offset(
unsigned int l,
unsigned int x,
unsigned int y )
const
113 return ( ( l * X ) + x ) * Y + y;
116 const Value & value(
unsigned int l,
unsigned int x,
unsigned int y )
const
118 return _data[ offset( l, x, y ) ];
121 unsigned int erase(
unsigned int l,
unsigned int x,
unsigned int y )
123 size_t offs = offset( l, x, y );
124 if ( _data[ offs ] != _invalid )
126 _data[ offs ] = _invalid;
133 void setValue(
const Value & val,
unsigned int l,
unsigned int x,
unsigned int y )
135 _data[ offset( l, x, y ) ] = val;
138 void setValueNoNewLabel(
const Value & val,
unsigned int l,
unsigned int x,
unsigned int y )
140 _data[ offset( l, x, y ) ] = val;
143 bool hasLabel(
unsigned int l,
unsigned int x,
unsigned int y )
const
145 return value( l, x, y ) != _invalid;
148 void getLabels( std::vector<unsigned int> & labels,
149 unsigned int x,
unsigned int y )
const
152 for (
unsigned int l = 0; l <
L; ++l )
153 if ( hasLabel( l, x, y ) )
154 labels.push_back( l );
157 unsigned int nbLabels(
unsigned int x,
unsigned int y )
const
160 for (
unsigned int l = 0; l <
L; ++l )
161 if ( hasLabel( l, x, y ) ) ++nb;
165 void display ( ostream & ,
unsigned int ,
unsigned int ,
unsigned int )
169 unsigned long long area()
const
171 return L * X * Y *
sizeof(
Value );
182 template <
typename Value>
183 class DynArrayXYOfMap {
184 typedef typename std::map<unsigned int, Value> MyMap;
188 typedef Value ValueType;
189 const unsigned int L;
190 const unsigned int X;
191 const unsigned int Y;
198 DynArrayXYOfMap(
unsigned int _L,
unsigned int _X,
unsigned int _Y )
199 :
L( _L ), X( _X ), Y( _Y )
201 _data =
new MyMap[ X * Y ];
209 size_t offset(
unsigned int x,
unsigned int y )
const
217 for (
unsigned int x = 0; x < X; ++x )
218 for (
unsigned int y = 0; y < Y; ++y )
219 _data[ offset( x, y ) ].clear();
223 const Value & value(
unsigned int l,
unsigned int x,
unsigned int y )
225 return _data[ offset( x, y ) ][ l ];
228 unsigned int erase(
unsigned int l,
unsigned int x,
unsigned int y )
230 return static_cast<unsigned int>(_data[ offset( x, y ) ].erase( l ));
234 void setValue(
const Value & val,
unsigned int l,
unsigned int x,
unsigned int y )
236 _data[ offset( x, y ) ][ l ] = val;
239 void setValueNoNewLabel(
const Value & val,
unsigned int l,
unsigned int x,
unsigned int y )
241 _data[ offset( x, y ) ][ l ] = val;
244 bool hasLabel(
unsigned int l,
unsigned int x,
unsigned int y )
const
246 return _data[ offset( x, y ) ].count( l ) != 0;
249 void getLabels( std::vector<unsigned int> & labels,
250 unsigned int x,
unsigned int y )
const
254 it_end = _data[ offset( x, y ) ].end();
256 labels.push_back( (*it).first );
259 unsigned int nbLabels(
unsigned int x,
unsigned int y )
const
261 return static_cast<unsigned int>(_data[ offset( x, y ) ].size());
264 void display ( ostream & ,
unsigned int ,
unsigned int ,
unsigned int )
269 unsigned long long area()
const
271 unsigned long long total = 0;
272 for (
unsigned int y = 0; y < Y; ++y )
273 for (
unsigned int x = 0; x < X; ++x )
275 unsigned int size = nbLabels( x, y );
276 total += ( size + 1 ) *
278 + 3 *
sizeof(
Value* )
288 #if __GXX_EXPERIMENTAL_CXX0X__ && ( __GNUC__ >= 4 ) && ( __GNUC_MINOR__ >= 6 )
300 template <
typename Value>
301 class DynArrayXYOfList {
302 typedef typename std::pair<uint16_t, Value> MyPair;
303 typedef typename std::forward_list<MyPair> MyList;
304 typedef typename MyList::iterator Iterator;
307 typedef Value ValueType;
308 const unsigned int L;
309 const unsigned int X;
310 const unsigned int Y;
318 DynArrayXYOfList(
unsigned int _L,
unsigned int _X,
unsigned int _Y )
319 :
L( _L ), X( _X ), Y( _Y )
321 _data =
new MyList[ X * Y ];
329 size_t offset(
unsigned int x,
unsigned int y )
const
337 for (
unsigned int y = 0; y < Y; ++y )
338 for (
unsigned int x = 0; x < X; ++x )
339 _data[ offset( x, y ) ].clear();
343 const Value & value(
unsigned int l,
unsigned int x,
unsigned int y )
345 MyList & list = _data[ offset( x, y ) ];
346 Iterator it = list.begin(), it_end = list.end();
347 for ( ; it != it_end; ++it )
349 if ( it->first == l )
return it->second;
351 ASSERT(it == it_end);
352 list.emplace_front( std::make_pair( l,
Value() ) );
353 return list.front().second;
356 unsigned int erase(
unsigned int l,
unsigned int x,
unsigned int y )
358 MyList & list = _data[ offset( x, y ) ];
359 Iterator it_prev = list.before_begin();
360 Iterator it = list.begin(), it_end = list.end();
361 for ( ; it != it_end; ++it )
363 if ( it->first == l )
365 list.erase_after( it_prev );
374 void setValue(
const Value & val,
unsigned int l,
unsigned int x,
unsigned int y )
376 MyList & list = _data[ offset( x, y ) ];
377 Iterator it = list.begin(), it_end = list.end();
378 for ( ; it != it_end; ++it )
380 if ( it->first == l )
387 list.emplace_front( std::make_pair( l, val ) );
390 void setValueNoNewLabel(
const Value & val,
unsigned int l,
unsigned int x,
unsigned int y )
392 MyList & list = _data[ offset( x, y ) ];
393 Iterator it = list.begin(), it_end = list.end();
394 for ( ; it != it_end; ++it )
396 if ( it->first == l )
403 list.emplace_front( std::make_pair( l, val ) );
406 bool hasLabel(
unsigned int l,
unsigned int x,
unsigned int y )
const
408 const MyList & list = _data[ offset( x, y ) ];
410 for ( ; it != it_end; ++it )
412 if ( it->first == l )
return true;
417 void getLabels( std::vector<unsigned int> & labels,
418 unsigned int x,
unsigned int y )
const
421 const MyList & list = _data[ offset( x, y ) ];
423 for ( ; it != it_end; ++it )
425 labels.push_back( (*it).first );
429 unsigned int nbLabels(
unsigned int x,
unsigned int y )
const
431 const MyList & list = _data[ offset( x, y ) ];
434 for ( ; it != it_end; ++it )
439 void display ( ostream & ,
unsigned int ,
unsigned int ,
unsigned int )
444 unsigned long long area()
const
446 unsigned long long total = 0;
447 for (
unsigned int y = 0; y < Y; ++y )
448 for (
unsigned int x = 0; x < X; ++x )
450 unsigned int size = nbLabels( x, y );
451 total +=
sizeof(
Value* )
476 template <
typename Value,
unsigned int L,
477 typename TWord,
unsigned int N,
unsigned int M >
478 class DynArrayXYOfLabelledMap {
481 typedef Value ValueType;
482 const unsigned int X;
483 const unsigned int Y;
486 MyLabelledMap* _data;
490 DynArrayXYOfLabelledMap(
unsigned int _X,
unsigned int _Y )
493 _data =
new MyLabelledMap[ X * Y ];
496 ~DynArrayXYOfLabelledMap()
501 size_t offset(
unsigned int x,
unsigned int y )
const
509 for (
unsigned int y = 0; y < Y; ++y )
510 for (
unsigned int x = 0; x < X; ++x )
511 _data[ offset( x, y ) ].clear();
515 const Value & value(
unsigned int l,
unsigned int x,
unsigned int y )
const
517 return _data[ offset( x, y ) ].fastAt( l );
521 void setValue(
const Value & val,
unsigned int l,
unsigned int x,
unsigned int y )
523 _data[ offset( x, y ) ][ l ] = val;
527 unsigned int erase(
unsigned int l,
unsigned int x,
unsigned int y )
529 return _data[ offset( x, y ) ].erase( l );
533 void setValueNoNewLabel(
const Value & val,
unsigned int l,
unsigned int x,
unsigned int y )
535 _data[ offset( x, y ) ].fastAt( l ) = val;
539 bool hasLabel(
unsigned int l,
unsigned int x,
unsigned int y )
const
541 return _data[ offset( x, y ) ].count( l );
545 void getLabels( std::vector<unsigned int> & labels,
546 unsigned int x,
unsigned int y )
const
548 _data[ offset( x, y ) ].labels().getLabels( labels );
552 unsigned int nbLabels(
unsigned int x,
unsigned int y )
const
554 return static_cast<unsigned int>(_data[ offset( x, y ) ].size());
556 inline void display ( ostream & ,
unsigned int ,
unsigned int x,
unsigned int y )
558 std::cerr << _data[ offset( x, y ) ] << endl;
562 unsigned long long area()
const
564 unsigned long long total = 0;
565 for (
unsigned int y = 0; y < Y; ++y )
566 for (
unsigned int x = 0; x < X; ++x )
568 unsigned int size = nbLabels( x, y );
569 total +=
sizeof( MyLabelledMap );
571 total += ( 1 + ( size - N - 1 ) / M ) * ( M *
sizeof(
Value ) + 8 );
620 #if (BOOST_MAJOR_VERSION >= 1 ) && (BOOST_MINOR_VERSION >= 47 )
621 template <
typename MapLXY>
623 generateData( MapLXY & m,
unsigned int L,
double proba_no_label,
double proba_label )
625 boost::random::mt19937 rng;
627 boost::random::uniform_smallint<> diceL(0, L-1);
628 boost::random::uniform_01<> diceDouble;
629 boost::random::geometric_distribution<> diceNbLabels( proba_label );
631 std::cerr <<
"E(Y)=" << ( (1-proba_label)/proba_label )
632 <<
" Var(Y)=" << ( (1-proba_label)/(proba_label*proba_label) )
634 unsigned int X = m.X;
635 unsigned int Y = m.Y;
636 unsigned int total = 0;
637 for (
unsigned int y = 0; y < Y; ++y )
638 for (
unsigned int x = 0; x < X; ++x )
640 if ( diceDouble( rng ) >= proba_no_label )
642 unsigned int nb = diceNbLabels( rng );
643 for (
unsigned int i = 0; i < nb; ++i )
645 unsigned int l = diceL( rng );
646 double v = diceDouble( rng );
647 m.setValue( v, l, x, y );
652 std::cerr <<
"- " << total <<
" insertions." << endl;
657 template <
typename MapLXY>
659 generateData( MapLXY & m,
unsigned int L,
double proba_no_label,
double proba_label )
663 boost::uniform_smallint<> diceL(0, L-1);
664 boost::uniform_01<> diceDouble;
665 boost::geometric_distribution<> nbLabelsDist( proba_label );
666 boost::variate_generator
668 boost::geometric_distribution<> > diceNbLabels( rng, nbLabelsDist);
670 std::cerr <<
"E(Y)=" << ( (1-proba_label)/proba_label )
671 <<
" Var(Y)=" << ( (1-proba_label)/(proba_label*proba_label) )
673 unsigned int X = m.X;
674 unsigned int Y = m.Y;
675 unsigned int total = 0;
676 for (
unsigned int y = 0; y < Y; ++y )
677 for (
unsigned int x = 0; x < X; ++x )
679 if ( diceDouble( rng ) >= proba_no_label )
681 unsigned int nb = diceNbLabels();
682 for (
unsigned int i = 0; i < nb; ++i )
684 unsigned int l = diceL( rng );
685 double v = diceDouble( rng );
686 m.setValue( v, l, x, y );
691 std::cerr <<
"- " << total <<
" insertions." << endl;
696 template <
typename MapLXY>
700 unsigned int X = m.X;
701 unsigned int Y = m.Y;
703 std::vector<unsigned int> labels;
704 for (
unsigned int y = 0; y < Y; ++y )
705 for (
unsigned int x = 0; x < X; ++x )
707 m.getLabels( labels, x, y );
708 for (
unsigned int i = 0; i < labels.size(); ++i )
709 sum += m.value( labels[ i ], x, y );
711 std::cerr <<
"- sum = " << sum <<
"." << endl;
715 template <
typename MapLXY>
719 unsigned int X = m.X;
720 unsigned int Y = m.Y;
722 for (
unsigned int y = 0; y < Y; ++y )
723 for (
unsigned int x = 0; x < X; ++x )
725 if ( m.hasLabel( l, x, y ) )
726 sum += m.value( l, x, y );
728 std::cerr <<
"- sum = " << sum <<
"." << endl;
732 template <
typename MapLXY>
734 locateThreeData( MapLXY & m,
unsigned int l1,
unsigned int l2,
unsigned int l3 )
736 unsigned int X = m.X;
737 unsigned int Y = m.Y;
738 unsigned int loc3 = 0;
739 for (
unsigned int y = 0; y < Y; ++y )
740 for (
unsigned int x = 0; x < X; ++x )
742 if ( ( m.hasLabel( l1, x, y ) )
743 && ( m.hasLabel( l2, x, y ) )
744 && ( m.hasLabel( l3, x, y ) ) )
747 std::cerr <<
"- " << loc3 <<
" places with " << l1 <<
", " << l2 <<
" ," << l3 << endl;
751 template <
typename MapLXY>
755 unsigned int X = m.X;
756 unsigned int Y = m.Y;
758 for (
unsigned int y = 0; y < Y; ++y )
759 for (
unsigned int x = 0; x < X; ++x )
761 nb += m.erase( l, x, y );
766 template <
typename MapLXY>
767 void generateStatsMultiMapXY(
const string & name,
769 const unsigned int L,
770 const unsigned int X,
771 const unsigned int Y,
772 double PROBA_NO_LABEL,
775 typedef typename MapLXY::ValueType
Value;
777 string msg =
"Generating statistics for " + name;
780 generateData< MapLXY > ( m, L, PROBA_NO_LABEL, PROBA_LABEL );
784 unsigned long long mem = m.area();
785 trace.
info() << mem <<
" bytes." << std::endl;
789 double sumAll = sumAllData< MapLXY > ( m );
790 trace.
info() <<
"- sum_all = " << sumAll <<
"." << endl;
794 double sum0 = sumOneData< MapLXY > ( m, 0 );
795 trace.
info() <<
"- sum_0 = " << sum0 <<
"." << endl;
799 double sum15 = sumOneData< MapLXY > ( m, 15 );
800 trace.
info() <<
"- sum_15 = " << sum15 <<
"." << endl;
804 unsigned int nbThree = locateThreeData< MapLXY > ( m, 3, 7, 8 );
805 trace.
info() <<
"- " << nbThree <<
" places (3, 7, 8) detected." << endl;
809 unsigned int nbErased = eraseOneData< MapLXY > ( m, 9 );
810 trace.
info() <<
"- " << nbErased <<
" values deleted." << endl;
818 std::cout << name <<
" " <<
L <<
" " << X <<
" " << Y
819 <<
" " << PROBA_NO_LABEL <<
" " << PROBA_LABEL
820 <<
" " <<
sizeof(
Value) <<
" " <<
sizeof(
Value*) <<
" " << mem
821 <<
" " << tgen <<
" " << tmem
822 <<
" " << tsumall <<
" " << tsum0 <<
" " << tsum15
823 <<
" " << tthree <<
" " << terase9 <<
" " << tclear
824 <<
" " << sumAll <<
" " << sum0 <<
" " << sum15
825 <<
" " << nbThree <<
" " << nbErased
829 #define GENERATE_STATS_NM( Word, N , M ) \
831 typedef DynArrayXYOfLabelledMap<Value,L,Word,N,M> MyArrayXYOfLabelledMap; \
832 MyArrayXYOfLabelledMap* anArrayXYOfLabelledMap = new MyArrayXYOfLabelledMap( X, Y ); \
833 generateStatsMultiMapXY( "DynArrayXYOfLabelledMap<double," #Word "," #N "," #M ">", \
834 *anArrayXYOfLabelledMap, L, X, Y, PROB_NO_DATA, PROB_ONE_DATA ); \
835 delete anArrayXYOfLabelledMap; \
842 int main(
int ,
char** )
844 typedef double Value;
845 static const unsigned int L = 16;
846 trace.
info()<<
"Test several multi-map structures and compute some statistics." <<std::endl <<
"With parameter: "<<std::endl
847 <<
"\t tested image size: 500 500"<<std::endl
848 <<
"Probability that there is no data at all at an image position (Bernouilli distribution): 0.5"
849 <<
"Probability for the geometric distribution of the number of data per image position (E(Y)=(1-p)/p, Var(Y)=(1-p)/p^2 :0.5"<< std::endl;
853 unsigned int X = 100;
854 unsigned int Y = 100;
856 double PROB_NO_DATA = 0.5;
861 double PROB_ONE_DATA = 0.5;
863 typedef DynArrayLXY<Value> MyArrayLXY;
864 MyArrayLXY* anArrayLXY =
new MyArrayLXY( L, X, Y, -1.0 );
865 generateStatsMultiMapXY(
"DynArrayLXY<double>",
866 *anArrayLXY, L, X, Y, PROB_NO_DATA, PROB_ONE_DATA );
869 typedef DynArrayXYOfMap<Value> MyArrayXYOfMap;
870 MyArrayXYOfMap* anArrayXYOfMap =
new MyArrayXYOfMap( L, X, Y );
871 generateStatsMultiMapXY(
"DynArrayXYOfMap<double>",
872 *anArrayXYOfMap, L, X, Y, PROB_NO_DATA, PROB_ONE_DATA );
873 delete anArrayXYOfMap;
875 #if __GXX_EXPERIMENTAL_CXX0X__ && ( __GNUC__ >= 4 ) && ( __GNUC_MINOR__ >= 6 )
876 typedef DynArrayXYOfList<Value> MyArrayXYOfList;
877 MyArrayXYOfList* anArrayXYOfList =
new MyArrayXYOfList( L, X, Y );
878 generateStatsMultiMapXY(
"DynArrayXYOfList<double>",
879 *anArrayXYOfList, L, X, Y, PROB_NO_DATA, PROB_ONE_DATA );
880 delete anArrayXYOfList;
void beginBlock(const std::string &keyword="")
MyDigitalSurface::ConstIterator ConstIterator
DGtal is the top-level namespace which contains all DGtal functions and types.
boost::uint8_t uint8_t
unsigned 8-bit integer.
int main(int argc, char **argv)
void erase(VContainer1 &c1, LContainer2 &c2, unsigned int idx)
unsigned int generateData(MapLXY &m, double proba_no_label, double proba_label)
double sumAllData(MapLXY &m)
unsigned int eraseOneData(MapLXY &m, unsigned int l)
double sumOneData(MapLXY &m, unsigned int l)
unsigned int locateThreeData(MapLXY &m, unsigned int l1, unsigned int l2, unsigned int l3)
void display(ostream &out, const AContainer &C)