diff --git a/VirtualRobot/Workspace/VoxelTreeND.hpp b/VirtualRobot/Workspace/VoxelTreeND.hpp index a2e106740284657097b4d481bb9587811a11a7df..7ceda02615f5215747cbc5d30e1cdac89d7e97b4 100644 --- a/VirtualRobot/Workspace/VoxelTreeND.hpp +++ b/VirtualRobot/Workspace/VoxelTreeND.hpp @@ -781,6 +781,17 @@ namespace VirtualRobot return root; } + void getMemoryConsumtion(long &storeMemStructure, long &storeMemData) + { + storeMemStructure = 0; + storeMemData = 0; + storeMemStructure += sizeof(VoxelTreeND<T,N>); + if (root) + { + root->accumulateMemoryConsumtion(storeMemStructure,storeMemData); + } + } + protected: /*! Returns voxel extends of element in given level (0<=level<maxLevels) and dimension dim (0<=dim<N) diff --git a/VirtualRobot/Workspace/VoxelTreeNDElement.hpp b/VirtualRobot/Workspace/VoxelTreeNDElement.hpp index 79e55b580be280bf329adccb55eb4656597945b1..32d891796c8436a9e365d02de29d5c472277fc18 100644 --- a/VirtualRobot/Workspace/VoxelTreeNDElement.hpp +++ b/VirtualRobot/Workspace/VoxelTreeNDElement.hpp @@ -50,16 +50,26 @@ namespace VirtualRobot { VR_ASSERT(master); this->tree = master; - //num_children = pow_int(2,N); - children = new VoxelTreeNDElement*[master->getNumChildren()]; - for (int i = 0; i < master->getNumChildren(); i++) + entry = NULL; + + if (level >= (tree->getMaxLevels() - 1)) { - children[i] = NULL; + leaf = true; + children = NULL; + } else + { + leaf = false; + //num_children = pow_int(2,N); + children = new VoxelTreeNDElement*[master->getNumChildren()]; + + for (int i = 0; i < master->getNumChildren(); i++) + { + children[i] = NULL; + } } - entry = NULL; - leaf = false; + memcpy(&(this->pos[0]), &(p[0]), sizeof(float)*N); //memcpy (&(this->extends[0]),&(extends[0]),sizeof(float)*N); this->level = level; @@ -377,12 +387,7 @@ namespace VirtualRobot bool read(const datablock& data, const std::map< unsigned int, VoxelTreeNDElement* >& idElementMapping) { deleteData(); - children = new VoxelTreeNDElement*[tree->getNumChildren()]; - - for (int i = 0; i < tree->getNumChildren(); i++) - { - children[i] = NULL; - } + entry = NULL; leaf = false; @@ -395,6 +400,12 @@ namespace VirtualRobot if (!leaf) { + children = new VoxelTreeNDElement*[tree->getNumChildren()]; + + for (int i = 0; i < tree->getNumChildren(); i++) + { + children[i] = NULL; + } for (int i = 0; i < num_children; i++) { if (data.children[i] > 0) @@ -415,6 +426,7 @@ namespace VirtualRobot } else { + children = NULL; entry = new T(data.entry); } @@ -425,6 +437,7 @@ namespace VirtualRobot VoxelTreeNDElement<T, N>* createChild(float p[N]) { + VR_ASSERT (!leaf); int indx = getChildIndx(p); if (indx < 0) @@ -521,6 +534,32 @@ namespace VirtualRobot return true; }; + void accumulateMemoryConsumtion(long &storeMemStructure, long &storeMemData) + { + storeMemStructure += sizeof(VoxelTreeNDElement<T,N>); + + if (entry) + { + VR_ASSERT(leaf); + storeMemData += sizeof(T); + } + else + { + VR_ASSERT(!leaf); + + // size of children array + storeMemStructure += tree->getNumChildren() * sizeof (VoxelTreeNDElement*); + + for (int i = 0; i < tree->getNumChildren(); i++) + { + if (children[i]) + { + children[i]->accumulateMemoryConsumtion(storeMemStructure,storeMemData); + } + } + } + } + void collectElements(std::vector<VoxelTreeNDElement*>& elements) { elements.push_back(this); @@ -590,12 +629,14 @@ namespace VirtualRobot void deleteData() { - for (int i = 0; i < tree->getNumChildren(); i++) + if (children) { - delete children[i]; + for (int i = 0; i < tree->getNumChildren(); i++) + { + delete children[i]; + } + delete[] children; } - - delete[] children; delete entry; children = NULL; entry = NULL; @@ -603,6 +644,7 @@ namespace VirtualRobot VoxelTreeNDElement<T, N>* getNextChild(int startIndex, int& storeElementNr) { + VR_ASSERT(!leaf); for (int i = startIndex; i < tree->getNumChildren(); i++) { if (children[i]) @@ -614,7 +656,6 @@ namespace VirtualRobot return NULL; } - //bool checkAllChildren(); VoxelTreeNDElement** children; T* entry; diff --git a/VirtualRobot/Workspace/tests/VoxelTreeTest.cpp b/VirtualRobot/Workspace/tests/VoxelTreeTest.cpp index 0a9eed2b3794389e80379a35ae0b4aa30ef5b4ae..31c14d2dc09bfc11493ed5fa8fe8d34c27276d9e 100644 --- a/VirtualRobot/Workspace/tests/VoxelTreeTest.cpp +++ b/VirtualRobot/Workspace/tests/VoxelTreeTest.cpp @@ -217,4 +217,40 @@ BOOST_AUTO_TEST_CASE(VoxelTreeNDIterator) BOOST_CHECK_EQUAL(nrElements, TEST_LOOPS); } + +BOOST_AUTO_TEST_CASE(VoxelTreeNDMem) +{ + const unsigned int N = 6; + float minB[N]; + float maxB[N]; + float discr[N]; + float extend = 10.0f; + + for (int i = 0; i < N; i++) + { + minB[i] = -100.0f; + maxB[i] = 100.0f; + discr[i] = extend; + } + + VirtualRobot::VoxelTreeND<unsigned char, N> v(minB, maxB, discr, true); + + float pos[N]; + for (int j = 0; j < N; j++) + { + pos[j] = float(rand() % 10000) / 10000.0f * 200.0f - 100.0f; + } + + v.setEntry(pos, rand() % 255); + + long structMem; + long dataMem; + v.getMemoryConsumtion(structMem,dataMem); + long expectedStructMem = sizeof(VirtualRobot::VoxelTreeND<unsigned char, N>) + sizeof(VirtualRobot::VoxelTreeNDElement<unsigned char, N>) * v.getMaxLevels(); // the basic data structures + expectedStructMem += (sizeof (VirtualRobot::VoxelTreeNDElement<unsigned char, N>*) * VirtualRobot::MathTools::pow_int(2, N)) * (N-1) ; // all except the leaf have to store an array of 64 pointers to the leafs + BOOST_CHECK_EQUAL(structMem, expectedStructMem); + BOOST_CHECK_EQUAL(dataMem, 1); +} + + BOOST_AUTO_TEST_SUITE_END()