[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: [lmi] Why does this crash?
From: |
Vaclav Slavik |
Subject: |
Re: [lmi] Why does this crash? |
Date: |
Sat, 17 Apr 2010 17:46:58 +0200 |
On Sat, 2010-04-17 at 16:43 +0200, Vadim Zeitlin wrote:
> The principle applies only when you assign the value returned by the
> function to a (const) reference. It doesn't apply if you use it in any
> other way.
Moreover, xmlwrapp is weird. It attempts to expose std iterators-like
interface in xml::node::iterator, but the internals of xmlwrapp
implementation make it impossible, so if you rely on exactly std
behavior, you may encounter weird and totally unexpected failures.
In particular: iterators' operator* returns a (const) xml::node&
reference. But internally, iterators don't iterate over xml::node, but
over libxml2's xmlNotePtrs. So when you call operator*, it creates a
"fake" xml::node corresponding to current position. This has two
consequences:
1. Equal iterators return different references:
xml::node root("root");
root.push_back(xml::node("child"));
xml::node::const_iterator a = root.find("child");
xml::node::const_iterator b = root.find("child");
const xml::node& na = *a;
const xml::node& nb = *b;
BOOST_CHECK( a == b ); // ok
BOOST_CHECK_EQUAL( &na, &nb ); // fails!
2. Iterator instance always returns the same reference, so you can't
remember it and change the iterator:
xml::node root("root");
root.push_back(xml::node("one"));
root.push_back(xml::node("two"));
xml::node::const_iterator i = root.begin();
const xml::node& one = *i;
BOOST_CHECK_EQUAL( one.get_name(), "one" );
++i;
const xml::node& two = *i;
BOOST_CHECK_EQUAL( two.get_name(), "two" );
BOOST_CHECK_EQUAL( one.get_name(), "one" ); // fails!
The second problem could be fixed by returning a value -- in light of
the principle you brought up, this should be backward compatible and not
result in any problems (or am I missing something?). Number one is a
harder problem and fixing it would cost some extra memory. I wonder if
any of these is worth fixing.
Vaclav