如何创建此标记联合的实例?有关已删除构造函数的编译器错误

Neo*_*ana 4 c++

这是我标记的联合:

struct UniformVariant
{
    enum class UNIFORM_TYPE {FLOAT, INT32, VEC2, VEC3, VEC4, MAT4} type;
    union
    {
        float f;
        int i;
        glm::vec2 v2;
        glm::vec3 v3;
        glm::vec4 v4;
        glm::mat4 m4;
    } value;
};
Run Code Online (Sandbox Code Playgroud)

如果我尝试这样使用它:

void some_function()
{
    UniformVariant v;
    some_other_function(v);
}
Run Code Online (Sandbox Code Playgroud)

我收到编译错误 use of deleted function 'UniformVariant::UniformVariant()'

它进一步表示它被隐式删除,因为默认定义是不正确的.所以我尝试添加一个构造函数UniformVariant

UniformVariant() : value(0.0f), type(UNIFORM_TYPE::FLOAT) { };
Run Code Online (Sandbox Code Playgroud)

但类似的问题.我认为这与在联合中包含类类型有关; 但我无法弄清楚正确使用它的语法.

Bar*_*rry 7

从[class.union]中的注释:

如果union的任何非静态数据成员具有非平凡的默认构造函数(12.1),复制构造函数(12.8),移动构造函数(12.8),复制赋值运算符(12.8),移动赋值运算符(12.8)或析构函数( 12.4),union的相应成员函数必须是用户提供的,否则将被隐式删除(8.4.3)union.

该联合中的一个类型具有非平凡的默认构造函数,因此您无法默认构造联合.考虑这种简单的再现:

struct X {
    X() { }  
};

struct Y {
    union {
        float f;
        X x;
    } value;
};

int main()
{
    Y y;
}
Run Code Online (Sandbox Code Playgroud)

X有一个非平凡的默认构造函数,因此Y::Y()隐式删除,因为隐式删除了匿名联合默认构造函数.

但是,您可以为该联合提供自己的默认构造函数:

union U {
    U() : f(0.f) { }

    float f;
    X x;
} value;
Run Code Online (Sandbox Code Playgroud)

现在这个例子编译.

但是,如果您只是实现自己的标记联合,我强烈建议您使用Boost.Variant.它非常有用,可以解决这个问题.