[MOAB-dev] r3522 - in MOAB/trunk: . test/obb
sjackson at cae.wisc.edu
sjackson at cae.wisc.edu
Mon Feb 1 17:03:46 CST 2010
Author: sjackson
Date: 2010-02-01 17:03:46 -0600 (Mon, 01 Feb 2010)
New Revision: 3522
Modified:
MOAB/trunk/MBOrientedBoxTreeTool.cpp
MOAB/trunk/MBOrientedBoxTreeTool.hpp
MOAB/trunk/test/obb/obb_test.cpp
MOAB/trunk/test/obb/obb_time.cpp
Log:
Add traversal statistics to OBB tree tool.
* All OBB tree queries now take an optional accumulator
structure into which information about the performance
of tree traversal is stored.
* These statistics are now gathered in the obb_test
program and printed if at least one -v argument given.
* These statistics are optionally gathered in the
obb_time program when -p argument given.
* Very simple testing with obb_time suggests that the
performance impact of gathering traversal statistics
is low (<5%). Statistics are not gathered when not
requested, so this performance loss is opt-in.
* Three OBB queries (sphere_intersect_triangles and both
variants of closest_to_location) did not previously keep
track of traversal depth, a value needed to compute these
statistics. They are now changed to track depth. I have not
tested the performance impact of this change, but I expect
it to be trivial.
Modified: MOAB/trunk/MBOrientedBoxTreeTool.cpp
===================================================================
--- MOAB/trunk/MBOrientedBoxTreeTool.cpp 2010-02-01 23:03:45 UTC (rev 3521)
+++ MOAB/trunk/MBOrientedBoxTreeTool.cpp 2010-02-01 23:03:46 UTC (rev 3522)
@@ -470,19 +470,27 @@
struct Data { MBEntityHandle set; int depth; };
MBErrorCode MBOrientedBoxTreeTool::preorder_traverse( MBEntityHandle set,
- Op& operation )
+ Op& operation,
+ TrvStats* accum )
{
MBErrorCode rval;
std::vector<MBEntityHandle> children;
std::vector<Data> the_stack;
Data data = { set, 0 };
the_stack.push_back( data );
+ int max_depth = -1;
while (!the_stack.empty())
{
data = the_stack.back();
the_stack.pop_back();
+ // increment traversal statistics
+ if( accum ){
+ accum->increment( data.depth );
+ max_depth = std::max( max_depth, data.depth );
+ }
+
bool descend = true;
rval = operation.visit( data.set, data.depth, descend );
if (MB_SUCCESS != rval)
@@ -511,17 +519,30 @@
return MB_MULTIPLE_ENTITIES_FOUND;
}
+ if( accum ){
+ accum->end_traversal( max_depth );
+ }
+
return MB_SUCCESS;
}
/********************** General Sphere/Triangle Intersection ***************/
+struct MBOBBTreeSITFrame {
+ MBOBBTreeSITFrame( MBEntityHandle n, MBEntityHandle s, int dp )
+ : node(n), surf(s), depth(dp) {}
+ MBEntityHandle node;
+ MBEntityHandle surf;
+ int depth;
+};
+
MBErrorCode MBOrientedBoxTreeTool::sphere_intersect_triangles(
const double* center_v,
double radius,
MBEntityHandle tree_root,
std::vector<MBEntityHandle>& facets_out,
- std::vector<MBEntityHandle>* sets_out )
+ std::vector<MBEntityHandle>* sets_out,
+ TrvStats* accum )
{
const double radsqr = radius * radius;
MBOrientedBox b;
@@ -539,13 +560,25 @@
std::vector<MBEntityHandle>::const_iterator t;
#endif
- std::vector<MBEntityHandle> stack, children;
- stack.reserve(60);
- stack.push_back(tree_root);
- stack.push_back(0);
+ std::vector<MBOBBTreeSITFrame> stack;
+ std::vector<MBEntityHandle> children;
+ stack.reserve(30);
+ stack.push_back( MBOBBTreeSITFrame( tree_root, 0, 0 ) );
+
+ int max_depth = -1;
+
while (!stack.empty()) {
- MBEntityHandle surf = stack.back(); stack.pop_back();
- MBEntityHandle node = stack.back(); stack.pop_back();
+ MBEntityHandle surf = stack.back().surf;
+ MBEntityHandle node = stack.back().node;
+ int current_depth = stack.back().depth;
+ stack.pop_back();
+
+ // increment traversal statistics.
+ if( accum ){
+ accum->increment( current_depth );
+ max_depth = std::max( max_depth, current_depth );
+ }
+
if (!surf && sets_out) {
rval = get_moab_instance()->get_entities_by_type( node, MBENTITYSET, sets );
if (!sets.empty())
@@ -569,10 +602,8 @@
return rval;
if (!children.empty()) {
assert(children.size() == 2);
- stack.push_back( children[0] );
- stack.push_back( surf );
- stack.push_back( children[1] );
- stack.push_back( surf );
+ stack.push_back( MBOBBTreeSITFrame( children[0], surf, current_depth + 1 ) );
+ stack.push_back( MBOBBTreeSITFrame( children[1], surf, current_depth + 1 ) );
continue;
}
@@ -619,6 +650,10 @@
}
}
}
+
+ if( accum ){
+ accum->end_traversal( max_depth );
+ }
return MB_SUCCESS;
}
@@ -737,12 +772,13 @@
double tolerance,
const double ray_point[3],
const double unit_ray_dir[3],
- const double* ray_length )
+ const double* ray_length,
+ TrvStats* accum )
{
MBRange boxes;
MBErrorCode rval;
- rval = ray_intersect_boxes( boxes, root_set, tolerance, ray_point, unit_ray_dir, ray_length );
+ rval = ray_intersect_boxes( boxes, root_set, tolerance, ray_point, unit_ray_dir, ray_length, accum );
if (MB_SUCCESS != rval)
return rval;
@@ -755,10 +791,11 @@
double tolerance,
const double ray_point[3],
const double unit_ray_dir[3],
- const double* ray_length )
+ const double* ray_length,
+ TrvStats* accum )
{
RayIntersector op( this, ray_point, unit_ray_dir, ray_length, tolerance, boxes_out );
- return preorder_traverse( root_set, op );
+ return preorder_traverse( root_set, op, accum );
}
MBErrorCode RayIntersector::visit( MBEntityHandle node,
@@ -984,11 +1021,12 @@
unsigned min_tolerace_intersections,
const double ray_point[3],
const double unit_ray_dir[3],
- const double* ray_length )
+ const double* ray_length,
+ TrvStats* accum )
{
RayIntersectSets op( this, ray_point, unit_ray_dir, ray_length, tolerance,
- min_tolerace_intersections, distances_out, sets_out, facets_out );
- return preorder_traverse( root_set, op );
+ min_tolerace_intersections, distances_out, sets_out, facets_out );
+ return preorder_traverse( root_set, op, accum );
}
@@ -996,11 +1034,12 @@
/********************** Closest Point code ***************/
struct MBOBBTreeCPFrame {
- MBOBBTreeCPFrame( double d, MBEntityHandle n, MBEntityHandle s )
- : dist_sqr(d), node(n), mset(s) {}
+ MBOBBTreeCPFrame( double d, MBEntityHandle n, MBEntityHandle s, int dp )
+ : dist_sqr(d), node(n), mset(s), depth(dp) {}
double dist_sqr;
MBEntityHandle node;
MBEntityHandle mset;
+ int depth;
};
MBErrorCode MBOrientedBoxTreeTool::closest_to_location(
@@ -1008,7 +1047,8 @@
MBEntityHandle root,
double* point_out,
MBEntityHandle& facet_out,
- MBEntityHandle* set_out )
+ MBEntityHandle* set_out,
+ TrvStats* accum )
{
MBErrorCode rval;
const MBCartVect loc( point );
@@ -1019,8 +1059,9 @@
std::vector<MBEntityHandle> children(2);
std::vector<double> coords;
std::vector<MBOBBTreeCPFrame> stack;
-
- stack.push_back( MBOBBTreeCPFrame(0.0, root, current_set) );
+ int max_depth = -1;
+
+ stack.push_back( MBOBBTreeCPFrame(0.0, root, current_set, 0) );
while( !stack.empty() ) {
@@ -1028,12 +1069,19 @@
MBEntityHandle node = stack.back().node;
double dist_sqr = stack.back().dist_sqr;
current_set = stack.back().mset;
+ int current_depth = stack.back().depth;
stack.pop_back();
// If current best result is closer than the box, skip this tree node.
if (dist_sqr > smallest_dist_sqr)
continue;
+ // increment traversal statistics.
+ if( accum ){
+ accum->increment( current_depth );
+ max_depth = std::max( max_depth, current_depth );
+ }
+
// Check if this node has a set associated with it
if (set_out && !current_set) {
sets.clear();
@@ -1076,12 +1124,12 @@
// push children on tree such that closer one is on top
if (dsqr1 < dsqr2) {
- stack.push_back( MBOBBTreeCPFrame(dsqr2, children[1], current_set ) );
- stack.push_back( MBOBBTreeCPFrame(dsqr1, children[0], current_set ) );
+ stack.push_back( MBOBBTreeCPFrame(dsqr2, children[1], current_set, current_depth+1 ) );
+ stack.push_back( MBOBBTreeCPFrame(dsqr1, children[0], current_set, current_depth+1 ) );
}
else {
- stack.push_back( MBOBBTreeCPFrame(dsqr1, children[0], current_set ) );
- stack.push_back( MBOBBTreeCPFrame(dsqr2, children[1], current_set ) );
+ stack.push_back( MBOBBTreeCPFrame(dsqr1, children[0], current_set, current_depth+1 ) );
+ stack.push_back( MBOBBTreeCPFrame(dsqr2, children[1], current_set, current_depth+1 ) );
}
}
else { // LEAF NODE
@@ -1120,6 +1168,10 @@
}
} // LEAF NODE
}
+
+ if( accum ){
+ accum->end_traversal( max_depth );
+ }
return MB_SUCCESS;
}
@@ -1128,7 +1180,8 @@
MBEntityHandle root,
double tolerance,
std::vector<MBEntityHandle>& facets_out,
- std::vector<MBEntityHandle>* sets_out )
+ std::vector<MBEntityHandle>* sets_out,
+ TrvStats* accum )
{
MBErrorCode rval;
const MBCartVect loc( point );
@@ -1140,8 +1193,9 @@
std::vector<MBEntityHandle> children(2);
std::vector<double> coords;
std::vector<MBOBBTreeCPFrame> stack;
-
- stack.push_back( MBOBBTreeCPFrame(0.0, root, current_set) );
+ int max_depth = -1;
+
+ stack.push_back( MBOBBTreeCPFrame(0.0, root, current_set, 0) );
while( !stack.empty() ) {
@@ -1149,12 +1203,19 @@
MBEntityHandle node = stack.back().node;
double dist_sqr = stack.back().dist_sqr;
current_set = stack.back().mset;
+ int current_depth = stack.back().depth;
stack.pop_back();
// If current best result is closer than the box, skip this tree node.
if (dist_sqr > smallest_dist_sqr + tolerance)
continue;
+ // increment traversal statistics.
+ if( accum ){
+ accum->increment( current_depth );
+ max_depth = std::max( max_depth, current_depth );
+ }
+
// Check if this node has a set associated with it
if (sets_out && !current_set) {
sets.clear();
@@ -1197,12 +1258,12 @@
// push children on tree such that closer one is on top
if (dsqr1 < dsqr2) {
- stack.push_back( MBOBBTreeCPFrame(dsqr2, children[1], current_set ) );
- stack.push_back( MBOBBTreeCPFrame(dsqr1, children[0], current_set ) );
+ stack.push_back( MBOBBTreeCPFrame(dsqr2, children[1], current_set, current_depth+1 ) );
+ stack.push_back( MBOBBTreeCPFrame(dsqr1, children[0], current_set, current_depth+1 ) );
}
else {
- stack.push_back( MBOBBTreeCPFrame(dsqr1, children[0], current_set ) );
- stack.push_back( MBOBBTreeCPFrame(dsqr2, children[1], current_set ) );
+ stack.push_back( MBOBBTreeCPFrame(dsqr1, children[0], current_set, current_depth+1 ) );
+ stack.push_back( MBOBBTreeCPFrame(dsqr2, children[1], current_set, current_depth+1 ) );
}
}
else { // LEAF NODE
@@ -1255,6 +1316,10 @@
}
} // LEAF NODE
}
+
+ if( accum ){
+ accum->end_traversal( max_depth );
+ }
return MB_SUCCESS;
}
@@ -1527,6 +1592,55 @@
}
+/********************* Traversal Metrics Code **************************/
+
+void MBOrientedBoxTreeTool::TrvStats::reset(){
+ nodes_visited_count.clear();
+ traversals_ended_count.clear();
+}
+
+void MBOrientedBoxTreeTool::TrvStats::increment( unsigned depth ){
+
+ while( nodes_visited_count.size() <= depth ){
+ nodes_visited_count.push_back(0);
+ traversals_ended_count.push_back(0);
+ }
+ nodes_visited_count[depth] += 1;
+}
+
+void MBOrientedBoxTreeTool::TrvStats::end_traversal( unsigned depth ){
+ // assume safe depth, because increment is always called on a given
+ // tree level first
+ traversals_ended_count[depth] += 1;
+}
+
+void MBOrientedBoxTreeTool::TrvStats::print( std::ostream& str ) const {
+
+ const std::string h1 = "OBBTree Depth";
+ const std::string h2 = " - NodesVisited";
+ const std::string h3 = " - TraversalsEnded";
+
+ str << h1 << h2 << h3 << std::endl;
+
+ unsigned num_visited = 0, num_traversals = 0;
+ for( unsigned i = 0; i < traversals_ended_count.size(); ++i){
+
+ num_visited += nodes_visited_count[i];
+ num_traversals += traversals_ended_count[i];
+
+ str << std::setw(h1.length()) << i
+ << std::setw(h2.length()) << nodes_visited_count[i]
+ << std::setw(h3.length()) << traversals_ended_count[i]
+ << std::endl;
+ }
+
+ str << std::setw(h1.length()) << "---- Totals:"
+ << std::setw(h2.length()) << num_visited
+ << std::setw(h3.length()) << num_traversals
+ << std::endl;
+
+}
+
/********************** Tree Statistics Code ****************************/
Modified: MOAB/trunk/MBOrientedBoxTreeTool.hpp
===================================================================
--- MOAB/trunk/MBOrientedBoxTreeTool.hpp 2010-02-01 23:03:45 UTC (rev 3521)
+++ MOAB/trunk/MBOrientedBoxTreeTool.hpp 2010-02-01 23:03:46 UTC (rev 3522)
@@ -25,6 +25,7 @@
#include <iosfwd>
#include <list>
+#include <vector>
class MBRange;
class MBOrientedBox;
@@ -120,6 +121,43 @@
MBEntityHandle& root_set_out,
const Settings* settings = 0 );
+ /**\brief Traversal statistics structure
+ *
+ * Structure to accumulate statistics on traversal performance. Passed optionally
+ * to query functions, this structure contains the count of nodes visited at each
+ * level in a tree, and the count of traversals that ended at each level.
+ * One TrvStats structure can be used with multiple OBB trees or multiple queries,
+ * or used on only a single tree or a single query.
+ *
+ * Note that these traversal statistics are not related to the stats() query below,
+ * which calculates static information about a tree. These statistics relate
+ * to a tree's dynamic behavior on particular operations.
+ */
+ class TrvStats{
+ public:
+
+ //! return counts of nodes visited, indexed by tree depth
+ const std::vector< unsigned >& nodes_visited() const ;
+ //! return counts of traversals ended, indexed by tree depth
+ const std::vector< unsigned >& traversals_ended() const ;
+ //! reset all counters on this structure
+ void reset();
+ //! print the contents of this structure to given stream
+ void print( std::ostream& str ) const ;
+
+ private:
+
+ std::vector< unsigned > nodes_visited_count;
+ std::vector< unsigned > traversals_ended_count;
+
+ void increment( unsigned depth );
+ void end_traversal( unsigned depth );
+
+ friend class MBOrientedBoxTreeTool;
+
+ };
+
+
/**\brief Intersect a ray with the triangles contained within the tree
*
* Intersect a ray with the triangles contained in the tree and return
@@ -136,7 +174,8 @@
double tolerance,
const double ray_point[3],
const double unit_ray_dir[3],
- const double* ray_length = 0 );
+ const double* ray_length = 0,
+ TrvStats* accum = 0 );
/**\brief Intersect ray with tree
*
@@ -153,7 +192,8 @@
double tolerance,
const double ray_point[3],
const double unit_ray_dir[3],
- const double* ray_length = 0 );
+ const double* ray_length = 0,
+ TrvStats* accum = 0 );
/**\brief Intersect ray with triangles contained in passed MBENTITYSETs */
MBErrorCode ray_intersect_triangles(
@@ -194,7 +234,8 @@
unsigned min_tolerace_intersections,
const double ray_point[3],
const double unit_ray_dir[3],
- const double* ray_length = 0 );
+ const double* ray_length = 0,
+ TrvStats* accum = 0 );
/**\brief Find closest surface, facet in surface, and location on facet
*
@@ -209,7 +250,8 @@
MBEntityHandle tree_root,
double* point_out,
MBEntityHandle& facet_out,
- MBEntityHandle* set_out = 0);
+ MBEntityHandle* set_out = 0,
+ TrvStats* accum = 0 );
/**\brief Find closest facet(s) to input position.
*
@@ -222,7 +264,8 @@
MBEntityHandle tree_root,
double tolerance,
std::vector<MBEntityHandle>& facets_out,
- std::vector<MBEntityHandle>* sets_out = 0 );
+ std::vector<MBEntityHandle>* sets_out = 0,
+ TrvStats* accum = 0 );
/**\brief Find facets intersected by a sphere
*
@@ -239,7 +282,8 @@
double radius,
MBEntityHandle tree_root,
std::vector<MBEntityHandle>& facets_out,
- std::vector<MBEntityHandle>* sets_out = 0 );
+ std::vector<MBEntityHandle>* sets_out = 0,
+ TrvStats* accum = 0 );
/**\brief Get oriented box at node in tree
*
@@ -342,7 +386,8 @@
* traversal will not descend to the children of the current node.
*/
MBErrorCode preorder_traverse( MBEntityHandle root_set,
- Op& operation );
+ Op& operation,
+ TrvStats* accum = 0 );
MBInterface* get_moab_instance() const { return instance; }
Modified: MOAB/trunk/test/obb/obb_test.cpp
===================================================================
--- MOAB/trunk/test/obb/obb_test.cpp 2010-02-01 23:03:45 UTC (rev 3521)
+++ MOAB/trunk/test/obb/obb_test.cpp 2010-02-01 23:03:46 UTC (rev 3522)
@@ -920,6 +920,8 @@
{ "skew miss", 0, box.center + box.dimensions(), box.dimensions() * box.axis[2] }
};
+ MBOrientedBoxTreeTool::TrvStats stats;
+
bool result = true;
const size_t num_test = sizeof(tests)/sizeof(tests[0]);
for (size_t i = 0; i < num_test; ++i) {
@@ -928,7 +930,7 @@
std::cout << " " << tests[i].description << " " << tests[i].point << " " << tests[i].direction << std::endl;
std::vector<double> intersections;
- rval = tool.ray_intersect_triangles( intersections, root_set, tolerance, tests[i].point.array(), tests[i].direction.array(), 0 );
+ rval = tool.ray_intersect_triangles( intersections, root_set, tolerance, tests[i].point.array(), tests[i].direction.array(), 0, &stats );
if (MB_SUCCESS != rval) {
if (verbosity)
std::cout << " Call to MBOrientedBoxTreeTool::ray_intersect_triangles failed." << std::endl;
@@ -955,7 +957,7 @@
const int NUM_NON_TOL_INT = 1;
std::vector<double> intersections2;
std::vector<MBEntityHandle> surf_handles, facet_handles;
- rval = tool.ray_intersect_sets( intersections2, surf_handles, facet_handles, root_set, tolerance, NUM_NON_TOL_INT, tests[i].point.array(), tests[i].direction.array(), 0 );
+ rval = tool.ray_intersect_sets( intersections2, surf_handles, facet_handles, root_set, tolerance, NUM_NON_TOL_INT, tests[i].point.array(), tests[i].direction.array(), 0, &stats );
if (MB_SUCCESS != rval) {
if (verbosity)
std::cout << " Call to MBOrientedBoxTreeTool::ray_intersect_sets failed." << std::endl;
@@ -1027,7 +1029,7 @@
if (!haveSurfTree) {
MBRange leaves;
std::vector<double> intersections;
- rval = tool.ray_intersect_boxes( leaves, root_set, tolerance, rays[i].array(), rays[i+1].array(), 0 );
+ rval = tool.ray_intersect_boxes( leaves, root_set, tolerance, rays[i].array(), rays[i+1].array(), 0, &stats );
if (MB_SUCCESS != rval) {
std::cout << "FAILED" << std::endl;
result = false;
@@ -1077,7 +1079,7 @@
else {
std::vector<double> intersections;
std::vector<MBEntityHandle> surfaces, facets;
- rval = tool.ray_intersect_sets( intersections, surfaces, facets, root_set, tolerance, 1000, rays[i].array(), rays[i+1].array(), 0 );
+ rval = tool.ray_intersect_sets( intersections, surfaces, facets, root_set, tolerance, 1000, rays[i].array(), rays[i+1].array(), 0, &stats );
if (MB_SUCCESS != rval) {
std::cout << "FAILED" << std::endl;
result = false;
@@ -1143,6 +1145,11 @@
}
}
+ if( verbosity > 1 ){
+ std::cout << "Traversal statistics for ray fire tests: " << std::endl;
+ stats.print(std::cout);
+ }
+
return result;
}
@@ -1252,6 +1259,9 @@
MBEntityHandle root_set,
bool have_surface_tree )
{
+ if (verbosity > 1)
+ std::cout << "beginning closest point tests" << std::endl;
+
MBErrorCode rval;
MBInterface* moab = tool.get_moab_instance();
MBEntityHandle set;
@@ -1265,6 +1275,8 @@
if (verbosity) std::cerr << "Invalid tree in do_closest_point_test\n";
return false;
}
+
+ MBOrientedBoxTreeTool::TrvStats stats;
// chose some points to test
MBCartVect points[] = { box.center + box.scaled_axis(0),
@@ -1297,7 +1309,8 @@
root_set,
t_result.array(),
t_tri,
- set_ptr );
+ set_ptr,
+ &stats );
if (MB_SUCCESS != rval) {
if (verbosity)
std::cout << "MBOrientedBoxTreeTool:: closest_to_location( " << points[i] << " ) FAILED!" << std::endl;
@@ -1342,6 +1355,11 @@
continue;
}
}
+
+ if( verbosity > 1 ){
+ std::cout << "Traversal statistics for closest point tests: " << std::endl;
+ stats.print(std::cout);
+ }
return result;
}
Modified: MOAB/trunk/test/obb/obb_time.cpp
===================================================================
--- MOAB/trunk/test/obb/obb_time.cpp 2010-02-01 23:03:45 UTC (rev 3521)
+++ MOAB/trunk/test/obb/obb_time.cpp 2010-02-01 23:03:46 UTC (rev 3522)
@@ -20,6 +20,7 @@
<< " -i - Specify total intersecting rays to fire." << std::endl
<< " Zero implies unbounded. Default: " << NUM_XSCT << std::endl
<< " -s - Use set-based tree." << std::endl
+ << " -p - Measure and report traversal performance statistics" << std::endl
<< " The input file should be generated using the '-s'" << std::endl
<< " option with 'obb_test'" << std::endl;
exit(1);
@@ -77,6 +78,7 @@
int num_xsct = NUM_XSCT;
const char* filename = 0;
bool do_sets = false;
+bool do_trv_stats = false;
// global to make accessable to signal handler
int rays = 0, xsct = 0, gen = 0;
@@ -131,6 +133,9 @@
else if (!strcmp( argv[i], "-s")) {
do_sets = true;
}
+ else if (!strcmp( argv[i], "-p")) {
+ do_trv_stats = true;
+ }
else if (filename) {
std::cerr << "Invalid options or multiple file names specified." << std::endl;
usage();
@@ -160,6 +165,11 @@
std::cerr << "Corrupt tree. Cannot get box for root node." << std::endl;
return 3;
}
+
+ MBOrientedBoxTreeTool::TrvStats* stats = NULL;
+ if( do_trv_stats ){
+ stats = new MBOrientedBoxTreeTool::TrvStats;
+ }
const unsigned cached = 1000;
std::vector<double> intersections;
@@ -198,10 +208,10 @@
if (do_sets) {
sets.clear();
facets.clear();
- rval = tool.ray_intersect_sets( intersections, sets, facets, root, 1e-6, 1, point.array(), dir.array() );
+ rval = tool.ray_intersect_sets( intersections, sets, facets, root, 1e-6, 1, point.array(), dir.array(), 0, stats );
}
else {
- rval = tool.ray_intersect_triangles( intersections, root, 1e-6, point.array(), dir.array() );
+ rval = tool.ray_intersect_triangles( intersections, root, 1e-6, point.array(), dir.array(), 0, stats );
}
if (MB_SUCCESS != rval) {
std::cerr << "Rayfire #" << rays << " failed." << std::endl;
@@ -225,6 +235,11 @@
<< xsct << " intersecting fires" << std::endl
<< (double)t/CLOCKS_PER_SEC << " seconds" << std::endl;
+ if( do_trv_stats ){
+ std::cout << "Traversal statistics: " << std::endl;
+ stats->print( std::cout );
+ }
+
return 0;
}
More information about the moab-dev
mailing list