通过迭代器清除内存时,会发生异常。
#include <stdint.h>
#include <vector>
#include "Shared.h"
using namespace std;
const int RangeItems = 3;
struct Anchor
{
uint16_t anchor_addr;
float range[RangeItems];
float dbm;
Anchor(uint16_t addr) : anchor_addr(addr), dbm(0) {}
};
struct Link
{
vector<Anchor> Anchors;
Link()
{
Anchors.reserve(10); //зарезервировать сразу N элементов
}
};
struct Link* init_link(uint16_t addr)
{
Link* l = new Link();
Anchor* a = new Anchor(addr);
l->Anchors.push_back(*a);
return l;
}
void add_To_End(struct Link* p, uint16_t addr)
{
Anchor* a = new Anchor(addr);
p->Anchors.push_back(*a);
}
Result delete_Anchor(Link* p, uint16_t addr)
{
for (auto it = p->Anchors.begin(); it != p->Anchors.end(); ++it)
{
Anchor a = *it;
if (a.anchor_addr == addr)
{
p->Anchors.erase(it);
delete &a; //ECXEPTION!!!!!
return Succsess;
}
}
return NotFound;
}
用向量测试
int main()
{
uwb_data= init_link(1);
add_To_End(uwb_data, 2);
add_To_End(uwb_data, 3);
add_To_End(uwb_data, 4);
auto res = delete_Anchor(uwb_data, 3);
}
当从vector中移除一个元素时,我想清除Anchor元素占用的内存,但是出现Exception。
与所有标准容器一样,向量会保留您放入其中的任何内容的副本。
那些。这里:
对象的副本进入向量,即
delete
你不需要在它上面调用它,你需要在原版上做它,在a
. 你没有,这就是为什么这里有内存泄漏。这也是崩溃的原因 - 您
delete
不是在调用您在堆上创建的对象,而是调用向量创建的副本。通常,在现代 C++ 中,您几乎不需要使用
new
,delete
除非您制作自己的矢量版本或类似的东西。添加这样的元素是正确的:
.emplace_back(addr);
或者.push_back(Anchor(addr));
(它也适用于您的课程.push_back(addr);
)。delete
当不需要删除时,就足够了erase
。Link
创建 via 也是没有意义的new
。简直了Link l; ... return l;
。然而,由于您是用 C ++ 而不是 C 编写的,因此struct Link
只需简单地编写就足够了Link
(除了结构定义本身之外的所有地方)。这就是发生的事情:
init_link(1);
创建Link
和 ,然后将副本放入为该对象分配内存的对象向量 中。Anchor
XL1
XA1
Anchor
Link
YA1
接下来,_调用 使用地址
add_To_End(uwb_data, 2);
创建并将副本放入(下对象的 )向量中,该向量为该对象分配内存。(向量中已经有两个这样的对象)Anchor
XA2
Anchor
uwb_data
YA2
调用:
delete_Anchor(uwb_data, 1)
找到uwb_data->Anchors
两个相似的对象并删除它们。因此,向量释放内存YA1
并YA2
有很多解决方案:
Anchor
在空闲内存中创建,而只是将其移动到向量中Anchors.emplace_back(Anchor(1))
(这种方式可能更好)push_back(*a)
释放内存а
之后(毕竟,无论如何都不再需要该对象,因为向量中有它的副本)