Проблема заключается в разметке памяти. Стандарт не гарантирует многого о разметке памяти, в частности, не гарантирует, что не существует смещения между производным и базовым классами ...
Например:
class Foo: public boost::noncopyable
{
public:
virtual ~Foo();
};
Поскольку boost::noncopyable
не имеет метода virtual
, в gcc (void*)(Foo*)&f
и (void*)(boost::noncopyable*)&f
будут иметь разные значения.
Но на практике это не имеет большого значения, потому что компилятор произведет необходимые настройки. То есть, если вы только сравниваете Foo*
, у вас должно быть все в порядке ...
... Кроме того, множественное наследование может нарушить это, если в вашей иерархии есть несколько Foo
подобъектов.
С другой стороны, вы должны оказаться в одном из двух случаев:
- либо нет иерархии (нет виртуальной), и тогда вы можете сравнить адреса объектов как есть
- или существует иерархия (и виртуальный метод), и вы используете
dynamic_cast<void*>(&f)
для получения адреса всего объекта.
Следовательно, как шаблонный метод это даст:
template <typename T, typename U>
bool have_same_dynamic_location(T const& t, U const& u)
{
return dynamic_cast<void*>(&t) == dynamic_cast<void*>(&u);
}
(что допустимо только в том случае, если и у T, и у U есть виртуальные методы)
person
Matthieu M.
schedule
03.12.2010