10 c语言程序,C语言编程(十)

原标题:C语言编程(十)

好久没更新这个系列了,今天接着说C语言中的结构体部分吧!主要介绍结构体定义、结构体变量定义、结构体变量的初始化、结构体变量之间赋值、结构体数组、结构体指针、结构体嵌套、结构体位段对齐等等。

知识点1【结构体的定义形式】

02d8336507f7dc839d704e0e0b31df02.png

39b479893d6797d23f25f5e99bfc69f2.png

知识点2【结构体变量的定义】

96a3d1ca9ba5e21fce42f5c1d5e616fb.png

8742d3bb896656abc9d30a68420ed9cd.png

知识点3【结构体变量的初始化】

357e7dc16694787f29972526105a4f8a.png

知识点4【结构体变量获取键盘输入】

9ff80622ef08f6c73169e7c3b6a9a95c.png

运行结果:

01c0b5d179630b1f37bddd79c4cd869d.png

知识点5【结构体变量间的赋值】

148f8b3def2f3d7ddc1fe5aae9023b66.png

运行结果:

ec69c12a0f1de1b965691ce0980b2793.png

struct stu tmp;交换俩个结构体变量

tmp = lucy;

lucy = bob;

bob = tmp;

知识点6【结构体数组】

3c46267ccb59e74069edbecb693964b5.png

6a9c3ec57c4cba96c36b9e8145230ced.png

//需求:定义一个结构体数组 有5个元素 获取键盘输入 求取平均年龄

73ea3f3b0cfc4750d26c4c65d86567fc.png

void test07()

{

struct stu arr[5];

memset(arr, 0,sizeof(arr));

int n = sizeof(arr)/sizeof(arr[0]);

//获取键盘输入

printf("请输入%d个学生的信息num name age\n",n);

int i=0;

for ( i = 0; i < n; i++)

{

scanf("%d %s %d", &arr[i].num, arr[i].name, &arr[i].age);

}

//统计总年龄

int sum = 0;

for ( i = 0; i < n; i++)

{

sum += arr[i].age;

}

printf("平均年龄为:%d\n",sum/n);

//按年龄 排序 冒泡排

for (size_t i = 0; i < n-1; i++)

{

for (size_t j = 0; j < n-i-1; j++)

{

if(arr[j].age > arr[j+1].age)//交换

{

struct stu tmp;

tmp = arr[j];

arr[j] = arr[j+1];

arr[j+1]=tmp;

}

}

}

printf("--------------\n");

for (i = 0; i < n; i++)

{

printf("num=%d, name=%s, age=%d\n", \

arr[i].num, arr[i].name, arr[i].age);

}

}

运行结果:

da513fd6a247fdfc4ea0e40512a9ab9b.png

知识点7【typedef】typedef 给已有的类型 取个别名。

typedef 不能创造 新的类型。

849670341de8c6084186f0a1a2d41d9b.png

案例:给数组取个别名

320e78800ca198defdc09a175fa5a143.png

案例:给函数指针 取个别名

e0808a581fca8fd0370069955ebb90c0.png

案例:给结构体取个别名

b7f65f7465b7c730e50b79bcd8ba75cb.png

ca980af9a8145bdcf56a55604bd4b0bb.png

知识点8【结构体指针】

typedef struct stu

{

int num;

char name[32];

float score;

}STU,*STU_P;

//STU就是struct stu的类型

//STU_P就是struct stu *的类型

void test04()

{

STU lucy={100, "lucy", 99.9f};

//STU_P p=&lucy;

STU *p = &lucy;

printf("num = %d,name=%s,score=%f\n", lucy.num, lucy.name,lucy.score );

//*p = *&lucy=lucy

printf("num = %d,name=%s,score=%f\n", (*p).num, (*p).name,(*p).score );

//直接通过p访问lucy成员

printf("num = %d,name=%s,score=%f\n", p->num, p->name, p->score );

//如果.或->左边 是变量 就用. 如果是地址就用->

printf("num = %d,name=%s,score=%f\n", (&lucy)->num, (&lucy)->name, (&lucy)->score );

}

运行结果:

8920483bdb006e3a97281b8d1a27ba5b.png

案例:堆区申请结构体空间

97a9ba35c322d9c5789a3a872a19a27b.png

知识点9【结构体指针作为函数的参数】

a80cba62e45cfcfeebd957a41097135b.png

知识点10【函数内部操作外部数组】

typedef struct stu

{

int num;

char name[32];

float score;

}STU,*STU_P;

STU* getSTUArray(int n)

{

return (STU *)calloc(n,sizeof(STU));

}

void myInputSTUArray(STU *arr, int n)

{

int i=0;

for(;i < n; i++)

{

printf("请输入第%d个学生的信息:",i+1);

//scanf("%d %s %f", &arr[i].num, arr[i].name, &arr[i].score );

scanf("%d %s %f", &(arr+i)->num, (arr+i)->name, &(arr+i)->score );

}

return;

}

void myPrintSTUArray(STU *arr, int n)

{

int i=0;

for(i = 0; i < n; i++)

{

printf("num=%d,name=%s,score=%f\n", (arr+i)->num, (arr+i)->name, (arr+i)->score );

}

return;

}

void test07()

{

STU *arr = NULL;

int n = 0;

printf("请输入学生的个数:");

scanf("%d", &n);

//根据学生的个数 从堆区申请结构体数组空间

arr = getSTUArray(n);

//获取键盘输入

myInputSTUArray(arr, n);

//遍历结构体数组

myPrintSTUArray(arr, n);

//释放空间

if(arr != NULL)

{

free(arr);

arr=NULL;

}

}

int main(int argc, char const *argv[])

{

test07();

return 0;

}

运行结果:

fec1f9600936181457d6488a98005ea5.png

知识点11【结构体对齐问题】

21e860dd73078ccc6ddf1f29b687eef6.png

步骤:

1、确定分配单位:每一行应该分配的字节数,由结构体中最大的基本类型的大小决定。

2、确定每个成员的起始位置的偏移量 = 成员的基本类型的整数(0~n)倍

3、收尾工作:结构体的总大小 == 分配单位的整数倍。

e5c83106c2b82a9cbed767db1b3beeb0.png

bf2bf16592520cff8ebeb0d655303296.png

案例:

6ba81ce88d22539d24a55271f52bb7c7.png

d9c2a2e9b77e98726a4a2c5555fe6208.png

结构体嵌套结构体:

typedef struct

{

int x;

int y;

}DATA3;

typedef struct

{

int a;

int b;

DATA3 c;//结构体嵌套结构体

}DATA4;

void test03()

{

//结构体嵌套结构体:访问到最底层

DATA4 data;

data.a = 10;

data.b = 20;

data.c.x = 30;

data.c.y = 40;

printf("%d\n", data.c.y);

}

运行结果:

25639886a8fc025edcff4a23f1368835.png

结构体嵌套结构体 的对齐问题

步骤:

1、确定分配单位:每一行应该分配的字节数,由所有结构体中最大的基本类型的大小决定。

2、确定每个成员的起始位置的偏移量 = 成员的基本类型的整数(0~n)倍

结构体成员的偏移量 = 被嵌套的结构体里面最大的基本类型的整数倍

结构体成员中成员偏移量 相对与 被嵌套的结构体

3、收尾工作:结构体的总大小 == 分配单位的整数倍。

结构体成员 的总大小 == 被嵌套的结构体里面最大的基本类型的整数倍

456d6b7b16a12311b7d83d62fbf90345.png

658a4389370077632a34bc796b86b3c9.png

案例:

8004453b0ff0bab6aa513ebda9bdda03.png

结构体对齐深思:

c6dc761d08564cac36f712bc606884fe.png

知识点11【强制类型对齐】

f7fbe4326baca8f6271a1e93e179c93f.png

步骤:

1、确定分配单位:每一行应该分配的字节数,min(value, 默认分配单位)

2、确定每个成员的起始位置的偏移量 = 成员的基本类型的整数(0~n)倍

3、收尾工作:结构体的总大小 == 分配单位的整数倍。

df0cc47d3000b1d8de7bed0c7a1cab2a.png

知识点12【结构体位段】

417138049d5f7b6b97ed6c4c6bfa59e6.png

位段的使用:

c37d2380c4ea3fe13d228178c89dc8d4.png

无意义位段:

f16f382b790631a0b80dbe211e8aa2c4.png

另起一个储存单元

dbfcdc8c4795fa5fa3bc6cc19dc1be94.png

应用场景:

责任编辑:

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值