C++ 非受限联合类型

什么是联合类型

在联合类型中多个对象可以共享一片内存,相应的这片内存也只能由一个对象使用。如下代码所示:

#include <iostream>
union U
{
 int x1;
 float x2;
};
int main()
{
 U u;
 u.x1 = 5;
 std::cout << u.x1 << std::endl;
 std::cout << u.x2 << std::endl;
 u.x2 = 5.0;
 std::cout << u.x1 << std::endl;
 std::cout << u.x2 << std::endl;
}

在上面的代码中联合类型U里的成员变量x1和x2共享同一片内存,所以修改x1的值,x2的值也会发生相应的变化,反之亦然。
 运行结果1

C++11 中的非受限联合类型

注意事项:在C++11中如果有联合类型中存在非平凡类型,那么这个联合类型的特殊成员函数将被隐式删除,也就是说
我们必须自己至少提供联合类型的构造和析构函数,例如:

#include <iostream>
#include <string>
#include <vector>
union U
{
 U() {} // 存在非平凡类型成员,必须提供构造函数
 ~U() {} // 存在非平凡类型成员,必须提供析构函数
 int x1;
 float x2;
 std::string x3;
 std::vector<int> x4;
};
int main()
{
 U u;
 u.x3 = "hello world";
 std::cout << u.x3;
}

注意:联合类型在析构的时候编译器并不知道当前激活的是哪个成员,所以无法自动调用成员的析构函数,必须由程序员编写代码完成这部分工作。所以可以看下面的代码。

推荐让联合类型的构造和析构函数为空,也就是什么也不做,并且将其成员的构造和析构函数放在需要使用联合类型的地方。修改上面的代码为:

#include <iostream>
#include <string>
#include <vector>
union U
{
 U() {}
 ~U() {}
 int x1;
 float x2;
 std::string x3;
 std::vector<int> x4;
};
int main()
{
 U u;
 // placement new 技巧来初始化构造
 new(&u.x3) std::string("hello world");
 std::cout << u.x3 << std::endl;
 u.x3.~basic_string();
 new(&u.x4) std::vector<int>;
 u.x4.push_back(58);
 std::cout << u.x4[0] << std::endl;
 u.x4.~vector();
}

placement new 在指定的内存地址上构造对象

Object * p = new (address) ClassConstruct(...);

注意

如果开发环境支持C++17标准,则大部分情况下我们可以使用 std:: variant 来代替联合体
具体variant的讲解见我以后的博客

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

强大的RGG

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值