Made SGPropertyNode::getPath extremely efficient: it now caches its

result, so after the first call for any node, it simply tests and
returns a pointer.  This also fixes the problem of buffer conflicts
with make_string.

Added SGPropertyNode::hasChild(const char * name, int index = 0) to
provide a syntactically-cleaner way to test for the existence of a
child node, i.e.

  for (int i = 0; i < 9; i++) {
    if (node->hasChild("foo", i))
      foo[i] = node->getChild("foo", i)->getDoubleValue();
  }
This commit is contained in:
david 2002-07-06 13:19:02 +00:00
parent d8b7e5b8fd
commit 90e8287f43
2 changed files with 32 additions and 12 deletions

View File

@ -635,6 +635,7 @@ SGPropertyNode::SGPropertyNode ()
: _name(copy_string("")),
_index(0),
_parent(0),
_path(0),
_path_cache(0),
_type(NONE),
_tied(false),
@ -652,6 +653,7 @@ SGPropertyNode::SGPropertyNode ()
SGPropertyNode::SGPropertyNode (const SGPropertyNode &node)
: _index(node._index),
_parent(0), // don't copy the parent
_path(0),
_path_cache(0),
_type(node._type),
_tied(node._tied),
@ -735,6 +737,7 @@ SGPropertyNode::SGPropertyNode (const char * name,
SGPropertyNode * parent)
: _index(index),
_parent(parent),
_path(0),
_path_cache(0),
_type(NONE),
_tied(false),
@ -753,6 +756,7 @@ SGPropertyNode::SGPropertyNode (const char * name,
SGPropertyNode::~SGPropertyNode ()
{
delete [] _name;
delete _path;
delete _path_cache;
clear_value();
delete _listeners;
@ -930,19 +934,25 @@ SGPropertyNode::removeChild (const char * name, int index, bool keep)
const char *
SGPropertyNode::getPath (bool simplify) const
{
if (_parent == 0)
return "";
string path = _parent->getPath(simplify);
path += '/';
path += _name;
if (_index != 0 || !simplify) {
char buffer[128];
sprintf(buffer, "[%d]", _index);
path += buffer;
// Calculate the complete path only once.
if (_path == 0) {
string path;
if (_parent == 0) {
path = "";
} else {
path = _parent->getPath(simplify);
path += '/';
path += _name;
if (_index != 0 || !simplify) {
char buffer[64];
sprintf(buffer, "[%d]", _index);
path += buffer;
}
}
_path = copy_string(path.c_str());
}
strncpy(_buffer, path.c_str(), MAX_STRING_LEN);
return _buffer;
return _path;
}
SGPropertyNode::Type

View File

@ -674,6 +674,15 @@ public:
const SGPropertyNode * getChild (int position) const;
/**
* Test whether a named child exists.
*/
bool hasChild (const char * name, int index = 0) const
{
return (getChild(name, index) != 0);
}
/**
* Get a child node by name and index.
*/
@ -1236,6 +1245,7 @@ private:
SGPropertyNode * _parent;
vector<SGPropertyNode_ptr> _children;
vector<SGPropertyNode_ptr> _removedChildren;
mutable char * _path;
hash_table * _path_cache;
Type _type;
bool _tied;