網站首頁 編程語言 正文
結構體
結構是一些值的集合,這些值稱為成員變量。結構的每個成員是不同類型的變量。
為什么要有結構體
比如說,描述一個學生時,需要有
- 名字
- 性別
- 年齡
- 身高
來一起描述,需要不同的變量,便有了結構體類型來描述
結構體的聲明
struct tag { member-lest//成員列表 }variable-list;//變量列表
例如一個學生
struct stu { char name[20]; char sex[5]; int age; int hight; };//這里有沒有變量列表都可以
struct stu { char name[20]; char sex[5]; int age; int hight; }s2,s3,s4;//s2,s3,s4全局變量 struct stu s5; int main() { struct stu s1;//結構體變量 }
特殊聲明
在聲明結構體時候,可以不完全聲明
struct { char c; int a; double a; }sa;//匿名結構體變量,必須在此處定義變量,否則以后不能使用 int main() { return 0; }
編譯器認為ps和&sa是兩種類型,這種寫法是錯誤的
數據結構:數據在內存中存儲的結構
關于列表
struct node { int date; struct node next; }; int main() { return 0; }
這樣無法判斷結構體大小 只需在結構體存放能找到下一個結構體內容的指針即可
struct node { int date; struct node* next; }; int main() { return 0; }
也可以這樣(重命名使用舉例)
typedef struct node { int date; struct node* next; }node; int main() { struct node n2 = { 0 };//2者都可以使用 node n = { 0 };//盡量不對結構體使用typedef }
結構體變量的定義和初始化
struct point { int x; int y; }p1; //聲明類型同時定義變量p1 struct point p2;//定義結構體變量p2 //初始化:定義變量的同時賦初值 struct point p3 = { 1,2 }; struct stu //類型聲明 { char name[15];//名字 int age; //年齡 }; struct stu s = { "zhangsan",20 };//初始化 struct node { int date; struct point p; struct node* next; }n1 = { 10,{4,5},NULL }; //結構體嵌套初始化 struct node n2 = { 20,{5,6},NULL };//結構體嵌套初始化
結構體大小計算
先來觀察下列代碼
#include <stdio.h> int main() { struct S1 { char c1; int i; char c2; }; printf("%d\n", sizeof(struct S1)); //練習2 struct S2 { char c1; char c2; int i; }; printf("%d\n", sizeof(struct S2)); //練習3 struct S3 { double d; char c; int i; }; printf("%d\n", sizeof(struct S3)); //練習4-結構體嵌套問題 struct S4 { char c1; struct S3 s3; double d; }; printf("%d\n", sizeof(struct S4)); return 0; }
發現并不是數據類型大小的簡單相加
存在對齊
如何計算?
首先得掌握結構體的對齊規則:
1. 第一個成員在與結構體變量偏移量為0的地址處。
2. 其他成員變量要對齊到某個數字(對齊數)的整數倍的地址處。
對齊數 = 編譯器默認的一個對齊數 與 該成員大小的較小值。
VS中默認的值為8
3. 結構體總大小為最大對齊數(每個成員變量都有一個對齊數)的整數倍。
4. 如果嵌套了結構體的情況,嵌套的結構體對齊到自己的最大對齊數的整數倍處,結構體的整
體大小就是所有最大對齊數(含嵌套結構體的對齊數)的整數倍。
為什么存在內存對齊 ?
大部分的參考資料都是如是說的:
1. 平臺原因(移植原因):
不是所有的硬件平臺都能訪問任意地址上的任意數據的;某些硬件平臺只能在某些地址處取某些特
定類型的數據,否則拋出硬件異常。
原文鏈接:https://blog.csdn.net/qq_62852431/article/details/122927549
相關推薦
- 2022-03-18 .NET?6開發TodoList應用之實現全局異常處理_實用技巧
- 2023-01-13 Python實現復制文檔數據_python
- 2022-06-07 如何在Python中妥善使用進度條詳解_python
- 2022-10-18 Golang?內存管理簡單技巧詳解_Golang
- 2022-06-07 Python利用capstone實現反匯編_python
- 2022-04-18 python?list?count統計個數的實現_python
- 2022-10-23 python運行或調用另一個py文件或參數方式_python
- 2022-09-17 oracle臨時表空間的作用與創建及相關操作詳解_oracle
- 最近更新
-
- window11 系統安裝 yarn
- 超詳細win安裝深度學習環境2025年最新版(
- Linux 中運行的top命令 怎么退出?
- MySQL 中decimal 的用法? 存儲小
- get 、set 、toString 方法的使
- @Resource和 @Autowired注解
- Java基礎操作-- 運算符,流程控制 Flo
- 1. Int 和Integer 的區別,Jav
- spring @retryable不生效的一種
- Spring Security之認證信息的處理
- Spring Security之認證過濾器
- Spring Security概述快速入門
- Spring Security之配置體系
- 【SpringBoot】SpringCache
- Spring Security之基于方法配置權
- redisson分布式鎖中waittime的設
- maven:解決release錯誤:Artif
- restTemplate使用總結
- Spring Security之安全異常處理
- MybatisPlus優雅實現加密?
- Spring ioc容器與Bean的生命周期。
- 【探索SpringCloud】服務發現-Nac
- Spring Security之基于HttpR
- Redis 底層數據結構-簡單動態字符串(SD
- arthas操作spring被代理目標對象命令
- Spring中的單例模式應用詳解
- 聊聊消息隊列,發送消息的4種方式
- bootspring第三方資源配置管理
- GIT同步修改后的遠程分支