C++ 正在visual studio中删除成员std::vector::data()

C++ 正在visual studio中删除成员std::vector::data(),c++,C++,我正在尝试构建一个与Python接口的库,但是我在VS2019中遇到了很多问题。我找到了一个简单的例子来说明我的问题: #include <vector> #include <iostream> class Foo { public: std::vector<double> bar; void fillBar(Foo& foo) { int nrElements = 100; for (int

我正在尝试构建一个与Python接口的库,但是我在VS2019中遇到了很多问题。我找到了一个简单的例子来说明我的问题:

#include <vector>
#include <iostream>

class Foo
{
public:
    std::vector<double> bar;

    void fillBar(Foo& foo)
    {
        int nrElements = 100;
        for (int i = 0; i < nrElements; ++i)
        {
            bar.emplace_back(0.0);
        }
    }
};

int main()
{
    Foo* foo = new Foo();

    std::cout << "Filling bar" << std::endl;
    foo->fillBar(*foo);

    std::cout << "deleting bar" << std::endl;
    delete foo->bar.data();

    std::cout << "The End" << std::endl;
}
#包括
#包括
福班
{
公众:
向量条;
空心填充条(Foo&Foo)
{
int n元素=100;
对于(int i=0;i
这不是打字错误。我同意这个例子有点派生,但为什么这不起作用呢

你根本不被允许这样做,因为 《C++标准(草案N47 13)中的“5.5.2.5删除”(ExpReleDe})清楚地表明:

在单对象delete表达式中,delete操作数的值可以是空指针 值,指向由以前的新表达式创建的非数组对象的指针,或指向子对象的指针(6.6.2) 表示此类对象的基类(第13条)。如果不是,则行为未定义。

未定义的行为,或通常简称UB,在“3.27[定义未定义]”中定义为

允许的未定义行为 从完全忽略情况到结果不可预测,再到在翻译或翻译过程中的行为 以环境特有的文件化方式执行程序(无论是否发布 对于诊断消息),终止转换或执行(发出诊断消息)

含义:您不允许删除由
std::vector::data()
给定的指针。如果您仍然这样做,并且通过
delete foo->bar.data()执行此操作
,您的程序是不确定的,因此我们讨论的是理性、常识、计算机编程之外的用例。它可以工作,也可以不工作,任何试图对此进行推理的行为都超出了通常被视为生产性计算机编程的范围。


当然,您可以
delete foo;
,因为
foo
实际上是指向由以前的新表达式创建的非数组对象的指针,但是
foo->data()
不是。它可能在内部是一些
std::vector
实现,但这既不保证,通常情况下也不允许,因为每个
std::vector
实现都必须
至少在销毁时删除其内部内存,导致双重删除,这也会调用但是,在分配和构造某些东西的意义上,大多数
std::vector
s甚至不使用
new

投票以键入错误的形式结束。
delete foo->bar.data()
应该是
delete foo;
因为您需要删除新建的指针,而不是指针指向的对象。您实际上不需要
new
,因此不需要
delete
“我想data()仍然会返回一个我可以删除的指针”--不,它从来没有这样做过。
向量管理它自己的内存。是什么让你认为乱搞它是你应该做的事情?@Frank你只能
删除
新的
编辑的东西。你没有
新的
什么
bar.data()
返回。您不能
删除它。如果您想释放内存,请让
bar
使用
clear()
为您执行此操作。它负责自己的内存,而您不负责。“为什么不工作?”-有很多原因我甚至不知道从哪里开始。1.vector的内部存储可能没有分配
new
,而是分配给了例如
malloc
。2.您正在使用
delete
,但您不知道
vector
是否使用了
new
new[]
(或参见1.)3.
数据()
可能不会指向它的内部存储。4.即使上述情况都没有发生,
vector
也会删除销毁期间分配给它的任何内存(尽管这不会发生在您的代码中,因为您正在泄漏
foo
)。此内存不是您要管理的,您不允许管理它。