c++ - 在 MSVC 上的数组初始化期间调用的析构函数没有复制或移动构造函数

标签 c++ visual-studio visual-c++

我已经在 MSVC 版本 19.10.25019.0 和 19.11.25547.0 的调试和发布版本中尝试过此操作,并获得了相同的结果。


以下程序打印 0 1 2 3 4 5。 我希望要么

  • 没有输出,或者
  • 移动或复制构造函数调用与析构函数调用的组合。

相反,似乎为 7 个元素中的 6 个调用了析构函数,并且没有进行复制或移动构造函数调用。

#include <iostream>

struct MyChar {
    MyChar(char c) : c{c}{}
    MyChar() = default;

    MyChar(const MyChar&) { std::cout << "copy"; };
    MyChar& operator=(const MyChar&) { std::cout << "assign"; return *this; };
    MyChar(MyChar&&) { std::cout << "move"; };
    MyChar& operator=(const MyChar&&) { std::cout << "move assign"; return *this; };

    ~MyChar() { std::cout << cnt++ << '\t'; }

    char c{'H'};
    static int cnt;
};

int MyChar::cnt{};

int main()
{
    auto arr1 = new MyChar[7]{'D'};
}

为什么析构函数在没有删除的情况下被调用 6 次(或者编译器没有通过复制或移动进行初始化)?

最佳答案

在 VC 编译器中尝试这个,并检查生成的汇编代码,这似乎是一个与 MyChar() = default 构造函数相关的编译器错误。将其替换为 MyChar() { } 可以消除意外的析构函数调用。

通过在析构函数中添加一些额外的代码,被销毁的对象是 arr1 的默认初始化成员。添加对 delete [] arr1 的调用,以及在析构函数中包含被销毁对象的地址,表明第一个元素被销毁一次,而其他 6 个被销毁两次 - 一次当arr1 被构造,并在进行 delete 调用时再次构造。

这应该报告给 Microsoft。它出现在VC2015和VC2017中。

关于c++ - 在 MSVC 上的数组初始化期间调用的析构函数没有复制或移动构造函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47395489/

相关文章:

c++ - xml 到 c++ : handling escape characters <=

visual-studio - -Ot 标志在 Visual Studio 2017 中代表什么?

c - 使用不同的结构对齐设置

c++ - VS2008中如何开启 "auto-build"选项

C++ 将字符串转换为 uint64_t

C++ Winsock send,recv - 它们是如何工作的

c++ - 在 Visual Studio IDE 中使用 C/C++ 预处理器宏

c++ - VST 插件 : How to implement a "lookahead" buffer?

c - 有没有办法在 GCC 中使用 fopen_s() 或至少创建一个关于它的#define?

c++ - 当窗口关闭时,我的析构函数会被调用吗?