版权声明:本文为博主原创文章,未经博主同意不得用于不论什么商业用途,转载请注明出处。 https://blog.csdn.net/luoweifu/article/details/33342965

你是否记得union这个东西,在上大学的时候我们用的是潭浩强的《C语言程序设计》,里面把它译作是共用体。“共用体”。尽管翻译得特别别扭,但却正好说明了它的特性和用途。

联合(union。也有翻译成共用体的)是一种特殊的结构(或说类)。

一个union能够有多个数据成员,可是在随意时刻仅仅有一个成员有值。

Union具有下面几个特点:

1.一个union能够有多个不同类型的数据成员。 但在某一时刻仅仅有一个成员有值(即仅仅有一个成员是有效的)。

 给union的某个成员赋值后,该union的其他成员就成没有定义的状态了。例如以下演示样例:

// 測试1
union Token
{
char cVal; //char 类型
int nVal; //int类型
double dVal; //double类型
}; void PrintToken(const Token& t)
{
cout << "char: " << t.cVal << endl;
cout << "int: " << t.nVal << endl;
cout << "double: " << t.dVal << endl;
} void TestUnion1()
{
cout << "Print first:"<< endl;
Token t;
t.cVal = 'k';
PrintToken(t); cout << endl << "Print second:"<< endl;
t.nVal = 5;
PrintToken(t);
cout << endl; cout << endl << "Print third:"<< endl;
t.dVal = 10.2;
PrintToken(t);
}

结果例如以下:

2.分配给一个union对象的存储空间,至少要能容纳它的最大的数据成员(即一个union的存储空间至少要为其各个成员的数据类型中占字节数最大的一个成员的字节大小)。

例如以下演示样例:

//測试2
union Token
{
char cVal; //char 类型。 1 个字节
int nVal; //int类型。 4个字节
double dVal; //double类型, 8个字节
}; union Token2
{
short snVal; //2个字节
int nVal; //4个字节
}; union Token3
{
int nVal; //4个字节
float fVal; //4个字节
long lVal; //4个字节
char arr[20]; //20个字节
}; void TestUnion2()
{
cout << "size of Token: " << sizeof(Token) << endl;
cout << "size of Token2:" << sizeof(Token2) << endl;
cout << "size of Token3:" << sizeof(Token3) << endl;
}

结果例如以下:

3.假设一个union结构中有多个同样类型的数据成员,则这些数据成员会有同样的值。

union应该是依据成员占用的内存最大的数据类型的大小分配一段内存空间。无论你使用的是那个成员变量,内存空间地址和大小都同样。当然以上就是依据測试的样例个人进行的判断,在这个样例中char的空间首地址输出有问题,可能跟操作系统有关系。我用的是Ubuntu的Linux操作系统,例如以下演示样例:

//測试3
union Token4
{
unsigned char cVal1;
unsigned char cVal2;
short int snVal;
int nVal;
long lVal;
long long llVal;
double dVal;
double dVal2;
}; void PrintToken4(const Token4& t)
{
cout << "char1: " << t.cVal1 << "\t\t\t" << &t.cVal1 << endl;
cout << "char2: " << t.cVal2 << "\t\t\t" << &t.cVal2 << endl;
cout << "short int:" << t.snVal << "\t\t\t" << &t.snVal << endl;
cout << "int: " << t.nVal << "\t\t" << &t.nVal << endl;
cout << "long: " << t.lVal << "\t\t" << &t.lVal << endl;
cout << "long long:" << t.llVal << "\t" << &t.llVal << endl;
cout << "double1: " << t.dVal << "\t\t" << &t.dVal << endl;
cout << "double2: " << t.dVal2 << "\t\t" << &t.dVal2 << endl;
} void TestUnion4()
{
cout << "Print first:"<< endl;
Token4 t;
t.cVal1 = 'A';
PrintToken4(t); cout << endl << "Print second:"<< endl;
t.nVal = 255;
PrintToken4(t);
cout << endl; cout << endl << "Print third:"<< endl;
t.dVal = 10.2;
PrintToken4(t);
}

结果例如以下:

watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQvbHVvd2VpZnU=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70/gravity/SouthEast" alt="" />

4.C++的早期版本号中(C++11标准之前)。union不能含有定义了拷贝构造函数或拷贝控制成员的类类型成员。但在C++11标准之后取消了这一限制。能够含有类的成员,如string及自定义的类。含有拷贝构造函数或拷贝控制成员的类类型成员的union比較复杂,能够去參考C++11标准的相关文档。

从Java到C++——union的使用方法的更多相关文章

  1. java.lang.String.getBytes(String charsetName)方法实例

    java.lang.String.getBytes(String charsetName) 方法编码将此String使用指定的字符集的字节序列,并将结果存储到一个新的字节数组. 声明 以下是java. ...

  2. java解析xml的三种方法

    java解析XML的三种方法 1.SAX事件解析 package com.wzh.sax; import org.xml.sax.Attributes; import org.xml.sax.SAXE ...

  3. Java并发编程基础--基本线程方法详解

    什么是线程 线程是操作系统调度的最小单位,一个进程中可以有多个线程,这些线程可以各自的计数器,栈,局部变量,并且能够访问共享的内存变量.多线程的优势是可以提高响应时间和吞吐量. 使用多线程 一个进程正 ...

  4. [java] 更好的书写equals方法-汇率换算器的实现(4)

    [java] 更好的书写equals方法-汇率换算器的实现(4) // */ // ]]>   [java] 更好的书写equals方法-汇率换算器的实现(4) Table of Content ...

  5. js,java,浮点数运算错误及应对方法

    js,java浮点数运算错误及应对方法 一,浮点数为什么会有运算错误 IEEE 754 标准规定了计算机程序设计环境中的二进制和十进制的浮点数自述的交换.算术格式以及方法. 现有存储介质都是2进制.2 ...

  6. Java小知识--length,length(),size()方法详细介绍

    Java中length,length(),size()区别 length属性:用于获取数组长度. eg: int ar[] = new int{1,2,3} /** * 数组用length属性取得长度 ...

  7. Java 静态变量,常量和方法

    static 关键字 例如:在球类中使用PI这个常量,可能除了本类需要这个常量之外,在另外一个圆类中也需要使用这个常量.这时没有必要 在两个类中同时创建PI这个常量,因为这样系统会将这两个不在同一个类 ...

  8. java内省机制及PropertyUtils使用方法

    背景 一般情况下,在Java中你可以通过get方法轻松获取beans中的属性值.但是,当你事先不知道beans的类型或者将要访问或修改的属性名时,该怎么办?Java语言中提供了一些像java.bean ...

  9. java中String对象的split方法

    在java.lang包中有String.split()方法,返回是一个String[]数组,今天碰到一个自己没注意的问题: 1.特殊分隔符 String str1 = "123|456|78 ...

随机推荐

  1. Tensortflow安装

    1.  CMD里面 pip install --upgrade --ignore-installed tensorflow

  2. 【转帖】WebRTC回声抵消模块简要分析

    webrtc 的回声抵消(aec.aecm)算法主要包括以下几个重要模块:回声时延估计:NLMS(归一化最小均方自适应算法):NLP(非线性滤波):CNG(舒适噪声产生).一般经典aec算法还应包括双 ...

  3. 04.如何升级扩展以支持Visual Studio 2019

    更新.vsixmanifest 我们需要对.vsixmanifest文件进行一些更新.首先,我们必须更新支持的VS版本范围 <InstallationTarget> 这是一个版本,支持Vi ...

  4. 03_springmvc整合mybatis

    一.整合思路 springmvc+mybaits的系统架构: 第一步整合dao层:mybatis和spring整合:通过spring管理mapper接口,使用mapper的扫描器自动扫描mapper接 ...

  5. <随便写>创建文件批处理文件

    创建一个text文档 写入想写的程序 将后缀改为bat 例如创建一个文件夹: 双击运行bat文件就可以创建文件夹 运行结果: 需要批量处理,就用for循环生成代码,粘贴上去就行了

  6. HtmlHelper2

    一.隐式从ViewBag取数据 1.action中的代码: ViewBag.UserName = "admin"; cshtml中的代码: @Html.TextBox(" ...

  7. ES6之主要知识点(九)Set和Map

    1.Set ES6 提供了新的数据结构 Set.它类似于数组,但是成员的值都是唯一的,没有重复的值. Set 本身是一个构造函数,用来生成 Set 数据结构. const s = new Set(); ...

  8. Java 使用模板生成 Word 文件---基于 Freemarker 模板框架

    Java项目引入 Freemarker 插件自行完成. 步骤如下: .编写 Word 模板,并将模板中要用代码动态生成数据用 Freemarker 变量取代,即${变量名},如${username}: ...

  9. C动态分配内存

    malloc分配内存时不初始化,calloc分配内存并进行初始化.

  10. Java虚拟机系列(一)---Java内存划分

    Java和C++之间有一堵由内存管理和垃圾收集技术所围成的“高墙”,墙外的人想进去,墙内的人却想出来.  ------摘自<深入理解Java虚拟机> 作为一个Java程序员,因为虚拟机的好 ...