使用C++ 11无限制联合时VS 2013异常

Jan*_*oux 0 c++ unions c++11 visual-studio-2013

考虑以下代码:

struct TNumeric {
    bool    Negative;
    wstring Integral;
    wstring Fraction;
};
union TValue {
    // The unnamed structs are needed because otherwise the compiler does not accept it...
    bool                Bit;
    struct{ TNumeric    Numeric; };
    struct{ wstring     Text; };
};

TNumeric Numeric;
TNumeric &rNumeric{ Numeric };
rNumeric.Integral = L"";
rNumeric.Integral.push_back( L'X' ); //OK, no problem

TValue Value;
TValue &rValue{ Value };
rValue.Text = L"";
rValue.Text.push_back( L'X' ); //OK, no problem

rValue.Numeric.Integral = L"";
rValue.Numeric.Integral.push_back( L'X' ); // Exception
Run Code Online (Sandbox Code Playgroud)

在发布模式下没有问题.在调试模式下运行时,xutility中类_Iterator_base12的方法_Adopt中的最后一个语句有一个异常:Access violation reading location 0x0000005C.

在_Adopt中,代码仅在运行时运行_ITERATOR_DEBUG_LEVEL == 2.我试过了

#define _ITERATOR_DEBUG_LEVEL 1
Run Code Online (Sandbox Code Playgroud)

添加到我的主程序中,但仍然定义为2.有没有办法禁用检查?

Ant*_*vin 5

VS 2013 不支持C++ 11不受限制的联合,即根据C++ 03实现联合:

具有非平凡构造函数(12.1),非平凡复制构造函数(12.8),非平凡析构函数(12.4)或非平凡复制赋值运算符(13.5.3,12.8)的类的对象不能成为工会的一员

您通过使用未命名的结构成功欺骗了编译器,但这并没有解决问题:对象不重要,VS2013不支持.

当您切换到更多符合C++ 11的编译器(例如VS 2015)时,您必须以一种安全构造/破坏/复制相应部分的方式为联合实现构造函数,析构函数,复制构造函数等.联盟.标准中有一个例子(我引用的是C++ 14草案N4140 [class.union]/4):

考虑具有类型和类型的非静态数据成员的u联合类型的对象.如果有一个非平凡的析构函数并且具有非平凡的构造函数(例如,如果它们声明或继承虚函数),则可以安全地将活动成员切换为使用析构函数和placement new运算符,如下所示:UmMnNMNumn

u.m.~M();
new (&u.n) N;
Run Code Online (Sandbox Code Playgroud)