2017-03-07 67 views
0

鉴于std::vector<A>::iteratorstd::map<A, B>::iterator,我该如何显式调用它们的析构函数?我不知道这些类型的实际名称,因为::iterator成员类型是特定于实现的类的typedef /别名。如何显式调用std迭代器的析构函数?

我问这个问题,因为我将这些迭代器存储在一个不受限制的C++联合中,并且Visual Studio要求我手动处理销毁。我可能只是不调用活动元素的析构函数,并假设迭代器不需要清理,但不好的做法反应。

+0

这听起来像你做错了。但我不知道你在做什么,所以我不能帮你做另一个,也许更好的方法。 – rubenvb

回答

3

像这样:

// let iter be vector<int>::iterator to be destroyed 
iter.std::vector<int>::iterator::~iterator(); 

我不知道这些类型的实际名称,这是因为:迭代成员类型的typedef /别名具体实现类。

没关系。类型别名也是类型名称。


LLVM似乎具有与该一个错误:https://bugs.llvm.org//show_bug.cgi?id=12350

直到它是固定的,作为一种解决方法,将非嵌套别名:

using iterator = std::vector<int>::iterator; 
iterator it; 
it.iterator::~iterator(); 

或参考类型模板参数(此代码来自bug报告):

template <typename T> 
inline void placement_delete(T *x) 
{ 
    // C++ lacks placement delete, so fake it with a function 
    x->~T(); 
} 
+0

如果迭代器类型是原始指针,则不起作用。 –

+0

@RichardCritten根据标准看起来不是一个问题:'显式调用析构函数的符号可以用于任何标量类型名称' – user2079303

+0

GCC似乎接受这一点,铛没有。 https://godbolt.org/g/V098YM –

0

大多数迭代器只是指向已分配内存的指针。除非使用新的迭代器创建

typedef std::vector<A>::iterator VecIter; 
VecIter* iter= new VecIter; 

没有必要删除。如果你正在使用new,那么你可以为迭代器变量显式调用delete。

delete iter; 
+0

我不是在调用迭代器的delete方法,而是显式地调用它的析构函数。 https://msdn.microsoft.com/en-us/library/6t4fe76c.aspx#Anchor_3 –

2
std::destroy_at(&iter); 

std::destroy和朋友是C + 17功能。如果你的编译器缺乏支持是微不足道的实施自己:

template <typename T> 
void destroy_at(T* p) { 
    p->~T(); 
} 

Source

+0

非常好!很高兴知道这存在。所以期待广泛的C++ 17支持! –

相关问题