我浏览了boost::hold_any
文件,发现了令我困惑的东西。如果我考虑通过我的问题的答案得到的信息:What happens if you call a destructor and use the allocated memory again for other objects?(在Mike Seymour的答案中)那么“禁止”操纵未被释放和重新分配的对象的记忆,放置一个不同类型的新对象。
我一直认为boost库符合标准,但如果我不完全错,那么boost::hold_any
将小对象或变量存储在它的内容指针(void* object
)本身的内存中,会破坏我在前面提到的答案中找到的规则。
我完全错了还是boost::hold_any
打破了标准?如果我错了,我的错误在哪里?
或者如果我是对的,如果它们包含可能导致未定义行为的部分,那么它们的可靠性是多么可靠?
嗯,我知道升级开发人员通常知道他们在做什么,但我听说经常在所有情况下都要避免未定义的行为,所以我有点好奇。
修改 我将代码示例更改为show,旧内容肯定会被破坏!
这是boost::hold_any
代码中我从以下地址获取信息的要点之一:
template <typename T>
basic_hold_any& assign(T const& x)
{
// are we copying between the same type?
spirit::detail::fxn_ptr_table<Char>* x_table =
spirit::detail::get_table<T>::template get<Char>();
if (table == x_table) {
// if so, we can avoid deallocating and re-use memory
table->destruct(&object); // first destruct the old content
if (spirit::detail::get_table<T>::is_small::value) {
// create copy on-top of object pointer itself
new (&object) T(x);
}
else {
// create copy on-top of old version
new (object) T(x);
}
}
else {
if (spirit::detail::get_table<T>::is_small::value) {
// create copy on-top of object pointer itself
table->destruct(&object); // first destruct the old content
new (&object) T(x);
}
else {
reset(); // first delete the old content
object = new T(x);
}
table = x_table; // update table pointer
}
return *this;
}
答案 0 :(得分:1)
在链接的答案中,UB是使用base* ptr
,而在调用placement new之后仍然指向该存储,并且在那里创建了不同类型的不同对象(用于调用{ {1}}就可以了。在Boost Any中并非如此。重用存储本身不是UB。