C语言——结构体与共用体
C语言——结构体与共用体
- 结构体
- 共用体
结构体
如果将复杂的复杂的数据类型组织成一个组合项,在一个组合项中包含若干个类型不同(当然也可以相同)的数据项。 C语言允许用户自己指定这样一种数据结构,它称为结构体。
结构体的语法定义:
struct 结构体名
{
成员列表
};
其中struct关键字表示在构造一个结构体类型,结构体名用来该结构体这个类型的名称,成员列表表示要描述的复杂数据中用到的具体的成员变量,成员列表的定义方式和普通变量的定义方式相同。例如下面定义一个student结构体类型:
struct student
{
char name[20];
int sno;
int age;
char sex[10];
float score;
};
在studen这个结构体中包含了姓名name、学号sno、年龄age;、性别sex[10];分数score;这些数据类型该结构体可以用来描述一个学生的基本信息。注意在结束一个结构体的定义时要在右括号“}”后面加上一个括号。
上述只是结构体的一种定义变量,还有其余两中结构体的定义方式:
1、
struct student
{
char name[20];
int sno;
int age;
char sex[10];
float score;
}s;
这里在定义结构体的同时也定义了一个结构体这种数据类型的变量s,这样写就可以直接使用该变量了。
2、
struct
{
char name[20];
int sno;
int age;
char sex[10];
float score;
}s;
这里在定义结构体类型的同时也定义了变量,可以省略结构体名,这种定义方式表示该结构体类型只能使用一次。
结构体的初始化
结构体初始化:
结构体的初始化也是采用初始化器去对结构体进行初始化,
struct student s = { “tom”, 1, 18, “man”, 99 };
结构体初始化的规则:
1、看每个成员变量,具体是什么数据类型。
2、根据各个成员变量自身的数据类型进行初始化。
3、初始化的顺序要按照定义的顺序依次进行初始化。
其实还可以在定义结构体的同时定义变量然后进行初始化:
struct student
{
char name[20];
int sno;
int age;
char sex[10];
float score;
}s = { “tom”, 1, 18, “man”, 99 };
结构体的成员变量引用的方式
结构体的引用成员变量方式一共有两种一个是通过结构体变量名.成员名,另一个是结构体指针->成员名,下面以一个例子来具体说明结构体成员变量的引用方式;
#include <stdio.h>struct student
{char name[20];int age;char sex[10];float score;
};int main(int argc, const char *argv[])
{struct student s = { "tom", 18, "man", 90 };printf("name : %s\n", s.name);printf("age : %d\n", s.age);printf("sex : %s\n", s.sex);printf("score : %.2f\n", s.score);return 0;
}
上述代码中定义了一个struct student的结构体类型然后在main函数定义变量的同时进行了初始化,在打印结构体的数据时采用了结构体变量名.成员名的方式。
#include <stdio.h>
#include <stdlib.h>void outputStu(struct student *s, int len)
{int i = 0;for(i = 0; i < len; ++i){printf("name : %s\n", (s+i)->name);printf("Sno : %d\n", (s+i)->Sno);printf("age : %d\n", (s+i)->age);printf("sex : %s\n", (s+i)->sex);printf("score : %.2f\n", (s+i)->score);printf("\n");}
}int main(int argc, const char *argv[])
{struct student s[3] = { { "tom", 1, 18, "m", 99 }, { "jerry", 2, 18, "w", 90 }, { "lucy", 3, 18, "w", 92 } };outputStu(s, 3);return 0;
}
上述程序将outputStu()函数的形参设置成结构体指针去接收一个结构体指针在打印结构体成员变量时采用了结构体指针->成员名的方式。
结构体的大小
结构体的大小遵循内存对齐规则:
结构体的对齐规则: //内存地址的对齐
1.在32位的平台上,默认都是按4字节对齐的。
2.对于成员变量,
各自在自己的自然边界上对齐。
char – 1字节
short – 2字节
int – 4字节
3.如果成员变量中有比4字节大。
此时整个结构体按照4字节对齐。 //32位的平台
4.如果成员变量中没有有比4字节大。
此时整个结构体按照最大的那个成员对齐。
注意在32位的平台下:
//如果有超过4字节 ,按照4字节对齐
//如果没有超过4字节的,则按成员变量中最大对齐
在64位的平台下:
//如果超过4字节的,按超过的最大的成员变量对齐
//如果没有超过4字节的,则按成员变量中最大对齐
首先要知道的是系统读取内存当中的数据时是4个字节4个字节地读取的,这样的读取方式能提高数据的读取效率和解析效率。
下面以一些例子来说明:
#include <stdio.h>struct s
{char a;short b;int c;
};int main(void)
{struct s aa;printf("sizeof(struct s) = %ld\n", sizeof(struct s));return 0;
}

我所用的平台是64为的平台所以下面也就主要说明64为平台下的内存对齐规则。在上述程序定义的结构体的成员变量所占的字节总共是7个字节,其中没有超过4字节的,则按成员变量中最大对齐char a;占一个字节它可以放在能被1整除的地址编号的内存当中short b;占两个字节放在a的后面且放在首地址编号能被2整除的内存当中,int c;占四个字节它放在首地址能被4整除的内存空间当中,最终整个结构体也要对齐该结构体没有超过4字节的,则按成员变量中最大对齐也就是8个字节。
#include <stdio.h>struct s
{char a;//一字节double b;//八字节int c;//四字节
};int main(void)
{struct s aa;printf("sizeof(struct s) = %ld\n", sizeof(struct s));return 0;
}

在上述程序定义的结构体的成员变量所占的字节总共是13个字节,其中有超过4字节的double类型,char a;占一个字节它可以放在能被1整除的地址编号的内存当中double b;占八个字节放在a的后面且放在首地址编号能被8整除的内存当中,int c;占四个字节它放在首地址能被4整除的内存空间当中,最终整个结构体也要对齐该结构体有超过4字节的,则按成员变量中最大对齐也就是24个字节。
共用体
共用体的语法:
union 共用体名
{
成员变量;
};
语法定义例子:
union demo
{
char a;
short b;
int c;
};
共用体成员变量共用的是一块内存空间且公用的是最大成员的空间 。
在使用共用体时要注意:
1.共用体初始化时,只能给一个值,默认时给到第一个成员的。
2.共用体变量中的值,取决与最后一次给到的值,还要看能影响几个字节。
利用共用体判断当前操作系统是大端还是小端存储:
#include <stdio.h>int isLittleEndian(void)
{union s{int a;char b;}c = { 1 };return c.b;
}int main(int argc, const char *argv[])
{printf("%d\n", isLittleEndian());return 0;
}

上述程序的共用体在初始化时给了一个1,一位int a;char b;共用的是同一块空间它们对应的首地址也是相同的,如果当前系统为小端存储那么1在存储时低位数据就会存放在地址所以如果是小端存储1就放在高位地址,则isLittleEndian()函数返回的是1反之就返回0。
相关文章:
C语言——结构体与共用体
C语言——结构体与共用体 结构体共用体 结构体 如果将复杂的复杂的数据类型组织成一个组合项,在一个组合项中包含若干个类型不同(当然也可以相同)的数据项。 C语言允许用户自己指定这样一种数据结构,它称为结构体。 结构体的语法…...
vs+qt项目转qt creator
1、转换方法 打开vs工程,右键项目,Qt->Create Base .pro File 后面默认OK 如果工程有include和lib路径需要配置,则转换后的工程,需要修改pro文件 2.修改pro文件 例如转换后的工程如下: 修改后 # ------------…...
微信小程序 checkbox 实现双向绑定以及特殊交互处理
wxml文件代码如下: <!--页面顶部 引入wxs文件--> <wxs module"tools" src"../../filter/tools.wxs"></wxs> ... <checkbox-group bindchange"checkboxChange"><label class"weui-cell weui-check__…...
我在高职教STM32——I2C通信之读写EEPROM(1)
大家好,我是老耿,高职青椒一枚,一直从事单片机、嵌入式、物联网等课程的教学。对于高职的学生层次,同行应该都懂的,老师在课堂上教学几乎是没什么成就感的。正是如此,才有了借助CSDN平台寻求认同感和成就感的想法。在这里,我准备陆续把自己花了很多心思设计的教学课件分…...
【ARM】应用ArmDS移植最小FreeRTOS系统
【更多软件使用问题请点击亿道电子官方网站】 一、文档背景 FreeRTOS(Free Real-Time Operating System)是一个开源的实时操作系统内核,广泛应用于嵌入式系统。它具有小巧、灵活、低功耗等特点,支持多任务调度、信号量、队列等实…...
golang下载、上传文件MD5高效计算方法,利用io.TeeReader函数特性 实时计算文件md5签名
在go语言的开发中,当我们在操作下载或者上传文件对象时, 我们可以利用golang内置的io包中的 TeeReader函数特性,高效实时计算文件的md5值。 方法如下: TeeReader高效计算文件md5示例 保存上传文件,并使用文件的md5签…...
TreeMap实现根据值比较
前言: TreeMap普通的排序方法都是根据键来比较来排序,本篇文章实现两种方式实现值排序 1.使用 SortedSet 和 Stream API 如果你想要一个持久化的排序结果,你可以使用 SortedSet 结构来存储键值对的条目。 TreeSet<Map.Entry<String, …...
2024前端面试(内容持续更新)
Vue篇 data为什么是个函数? 在Vue中,data必须是一个函数,这是因为当data是函数时,每个组件实例化时都会调用该函数,返回一个新的数据对象,从而保证每个组件实例拥有独立的数据,避免数据冲…...
接口基础知识5:详解request headers(一篇讲完常见字段)
课程大纲 一、请求头的定义 HTTP请求头部(HTTP Request Headers):HTTP协议中的一部分,用于在客户端和服务器之间传递附加信息。这些头部字段提供了关于请求、客户端环境、或请求的上下文的信息。 请求头是键值对的形式ÿ…...
mac的node使用
查看当前Node和npm版本 node -v npm -v安装"n"版本管理工具 sudo npm install -g n 更新node版本 sudo n stable // 稳定版本 sudo n lts // 最新稳定版本 sudo n latest // 最新版本 sudo n xx.xx // 更新到指定版本查看node版本安装集合 n ls切换对应node版…...
HTML - 简易版打字练习
1. 赛博朋克风格的视觉设计 颜色与渐变:通过linear-gradient设置了背景的颜色渐变,使用高饱和度的霓虹色彩(如橙色、绿色和蓝色)来营造赛博朋克的视觉效果。这种配色方案是赛博朋克风格的典型元素。 立体感和阴影:使用…...
【生成式人工智能-四-chatgpt的训练过程-pretrain预训练自督导式学习督导式学习】
大模型是怎么被训练出来的具有人类智慧的 阶段一训练-自我学习-具备知识训练资料self-supervised learning(自督导式学习) 阶段二-怎么让模型具备人的智慧supervised learning 督导式学习预训练pretrain为什么要用预训练的模型?Adapter逆向工…...
期权价格的奥秘:深入理解影响因素
在金融市场中,期权作为一种衍生工具,为投资者提供了风险管理和资产增值的多种可能性。期权价格的波动往往令人着迷,但其背后的定价机制却充满了复杂性。本文将带您探索期权价格变化的奥秘,并尝试以浅显易懂的方式,解析…...
STM32-USART时序与寄存器状态分析
一、时序分析 在UART(通用异步收发传输)通信中,信号线上的状态分为两种:逻辑1(高电平)和逻辑0(低电平)。在空闲状态下,数据线应保持逻辑高电平。UART协议中的各个信号位具…...
从零安装pytorch并在pycharm中使用
背景介绍 目前主流使用的工具有Facebook搞的pythorch和谷歌开发的tensorflow两种,二者在实现理念上有一定区别,pytorch和人的思维模式与变成习惯更像,而tensorflow则是先构建整体结构,然后整体运行,开发调试过程较为繁…...
开源AI工具FastGPT和RagFlow对比
FastGPT和RagFlow都是基于大型语言模型(LLM)的先进AI系统,它们在多个方面有着各自的特点和优势。 以下是对两者性能的详细对比: 一、系统架构与功能 FastGPT: 数据收集:通过从互联网上收集大量的文本数…...
第N2周:NLP中的数据集构建
对于初学者,NLP中最烦人的问题之一就数据集的构建问题,处理不好就会引起shape问题(各种由于shape错乱导致的问题)。这里给出一个模版,大家可根据这个模版来构建。 torch.utils.data是PyTorch中用于数据加载和预处理的…...
AI助力浮雕创作!万物皆可浮雕?Stable Diffusion AI绘画【浮雕艺术】之文生浮雕!
前言 对于浮雕艺术,其实并不了解。但有幸能和“细辛”前辈结识,对浮雕有了简单的了解,浮雕图案的传统方式是先由画师画出图,然后由雕刻师雕刻。画师画图归为浮雕的设计阶段,画师会绘制出浮雕的设计图,这为…...
你觉得大模型时代该出现什么?
大模型的概念都火了两年了,之前各种媒体吹嘘大模型的出现是类似“蒸汽机时代”、“iPhone时刻”等等。那为什么我们期待的结果都没出现呢?咱们先一起回顾下历史。 1、蒸汽机时代 1.1、蒸汽机历史 许多人都在讨论大模型时代好像只是概念在火࿰…...
JS【详解】事件委托
事件委托的简介 事件委托(Event Delegation)是 JS 处理事件的一种技术:不直接在目标元素上设置事件监听器,而是在其父元素或祖先元素上设置监听器,然后利用事件冒泡机制来捕获和处理事件。 事件委托的好处 减少内存占用…...
假芯片识别与防范:工程师实战指南
1. 假芯片泛滥:半导体行业的隐秘危机最近在调试一块电路板时,我发现一个奇怪的现象:明明使用的是同型号的MCU,但部分板子的功耗异常偏高。经过一周的排查,最终发现问题出在芯片上——我们采购到了一批"套牌"…...
单片机通信协议详解:IIC、SPI、UART与CAN对比
1. 单片机通信协议概述在嵌入式系统开发中,单片机的通信能力直接影响着整个系统的架构设计和性能表现。作为一名有着十年嵌入式开发经验的工程师,我经常需要根据项目需求选择合适的通信协议。目前主流的单片机通信方式包括IIC、SPI、UART/USART、CAN等&a…...
开发者专属:OpenClaw调用Qwen3-14B完成API自动化测试
开发者专属:OpenClaw调用Qwen3-14B完成API自动化测试 1. 为什么选择OpenClaw做API测试自动化 去年接手一个金融数据平台项目时,我遇到了API测试的瓶颈——每次迭代需要手动执行200个Postman测试用例,还要人工核对返回结果。这种重复劳动不仅…...
如何用Lingui.js在SSG项目中实现完美国际化:终极指南
如何用Lingui.js在SSG项目中实现完美国际化:终极指南 【免费下载链接】js-lingui 🌍 📖 A readable, automated, and optimized (2 kb) internationalization for JavaScript 项目地址: https://gitcode.com/gh_mirrors/js/js-lingui …...
Pixel Aurora Engine镜像部署:支持RTX 3060及以上显卡的轻量级方案
Pixel Aurora Engine镜像部署:支持RTX 3060及以上显卡的轻量级方案 1. 项目概览 Pixel Aurora Engine是一款专为像素艺术创作设计的AI绘图工作站,采用复古8-bit游戏风格界面,让AI艺术创作变得像玩游戏一样有趣。这个轻量级解决方案特别针对…...
工业冷水机控制程序西门子1200plc含压缩机,电子膨胀阀控制策略,饱和温度计算公式
工业冷水机控制程序西门子1200plc含压缩机,电子膨胀阀控制策略,饱和温度计算公式凌晨三点钟的冷水机组房,设备轰鸣声中闪烁着PLC运行指示灯。手指划过TP1200触摸屏的瞬间,压缩机启动电流曲线在屏幕上划出漂亮的爬坡轨迹——这就是…...
OpenClaw二次开发:基于Qwen3.5-9B定制个性化技能模块
OpenClaw二次开发:基于Qwen3.5-9B定制个性化技能模块 1. 为什么需要自定义技能模块 去年冬天,我发现自己每天早晨都要手动查询天气来决定穿什么衣服。作为一个技术爱好者,我开始思考:能否让OpenClaw自动完成这个任务?…...
DHL集团与中国外运将进一步深化全球业务协同
、美通社消息:近日,DHL集团与中国外运正式签署谅解备忘录。双方宣布,将在过往坚实合作的基础上,进一步深化全球业务协同,共同开启新一轮战略对话与长远布局。此次签约正值双方合资公司——中外运敦豪成立四十周年。作为…...
Word多级列表编号消失?别慌!用这个宏代码一劳永逸(附详细操作截图)
Word多级列表编号消失?三步根治方案与宏代码实战 写论文时目录编号突然消失?项目报告的多级列表格式莫名混乱?这种"幽灵问题"几乎困扰过每个深度使用Word的用户。传统方法往往只能临时修复,下次打开文档时问题依旧——直…...
WPF高性能绘图避坑指南:为什么你的心电图曲线会让CPU飙升?
WPF高性能绘图避坑指南:为什么你的心电图曲线会让CPU飙升? 在医疗监护设备或金融行情系统中,实时波形渲染的卡顿可能直接导致误诊或交易延迟。当你的WPF应用在绘制每秒60帧的心电图时突然出现CPU占用率突破90%,这往往不是硬件性能…...
