C语言学习---构造数据类型与位运算

一 .构造数据类型

(一)基础定义与使用

结构体让我们能自定义复合数据类型,把多个不同类型(如 intchar 数组等 )的变量 “打包” 成一个整体 。定义形式如下:

struct 结构体名 {
    数据类型1 成员变量1;
    数据类型2 成员变量2;
    // 可继续扩展更多成员
};

像日期、时间、学生信息等场景都能用结构体描述,比如定义学生结构体:

struct student {
    char name[32];
    char sex;
    int age;
    int score;
};

(二)变量定义与初始化

  • 全部初始化:按成员顺序赋值,如 struct student stu = {"zhangsan", 'm', 18, 90}; ,一次性给所有成员设定初始值。

  • 局部初始化:只给部分成员赋值,未赋值成员自动为 0(数值类型 )或空(字符数组等 ),示例:

struct student stu = {
    .name = "zhangsan",
    .score = 90
};

(三)成员访问与存储特性

访问方式:有两种常用方式,通过 . 访问结构体变量成员(如 stu.name ),通过 -> 访问结构体指针成员(如 p->name ,p 是结构体指针 )。                                                                                存储规则:结构体要考虑内存对齐,成员需存放在自身类型长度整数倍地址,结构体整体大小是最大成员类型长度的整数倍,这是为了提升 CPU 访问内存效率。

(四)传参与数组应用

传参:传结构体地址更高效,避免大结构体拷贝,函数参数可设为 struct student *prtp ;若传值,参数为 struct student tmp ,但数据量大时不推荐。

结构体数组:元素个数需是常量,用于批量存储同类型结构体数据,初始化可逐个元素赋值,也可指定成员初始化,比如:

struct student s[3] = {
    {"zhangsan", 'm', 19, 100},
    {"lisi", 'f', 18, 90},
    {"wanger", 'm', 19, 60}
};

struct student s[3] = {
[1] = {
.name = "zhangsan",
.score = 90,
},
};

二、共用体:内存共享的灵活类型

(一)核心特性

共用体(联合)与结构体不同,它的成员变量共享同一块内存空间 。定义形式:

union 共用体名 {
    数据类型1 成员变量1;
    数据类型2 成员变量2;
    // 其他成员
};

它常用于节省内存或函数多参数场景,比如判断内存大小端(小端:低地址存低数据位;大端:低地址存高数据位 ),利用共用体实现:

#include <stdio.h>
union s {
    char a;
    int b;
};
int main(void) {
    union s s1;
    s1.b = 1;
    if(s1.a)
        printf("小端存储\n");
    else
        printf("大端存储\n");
    return 0;
}

(二)使用要点

由于成员共享内存,同一时刻只有一个成员数据有效,使用时要注意逻辑控制,避免数据混乱。

三、枚举:常量集合的简洁定义

(一)定义与特性

枚举用于定义一组命名常量,形式为:

enum 枚举类型名 {
    常量1,
    常量2,
    // 更多常量
};

枚举常量默认是 int 类型,第一个常量默认值为 0,后续常量值是前一个常量值 +1 ,也可在定义时手动赋值修改,比如 enum Week {Mon=1, Tue, Wed}; ,让 Mon 为 1 ,Tue 为 2 等,方便程序中用有意义的名称代替魔法数字(直接写的无意义数字 )。

(二)应用场景

在表示状态、选项等固定值集合场景好用,像表示星期、性别选项(不过性别用字符或布尔可能更直观 )、错误码分类等,让代码可读性更高,语义更清晰。

四、内存管理:合理分配与释放内存

(一)内存区域划分

C 程序运行时内存分不同区域,像全局变量、静态变量存全局 / 静态存储区,局部变量在栈区,动态分配内存(堆区 )等。堆区内存需要我们手动管理,合理申请和释放。

(二)动态内存函数

malloc:申请堆区内存,参数是要申请的字节数,返回申请到的内存首地址(void* 类型 ),失败返回 NULL ,示例 int *p = (int*)malloc(10 * sizeof(int)); ,申请能存 10 个 int 的空间。free:释放 malloccalloc 等申请的堆内存,参数是要释放的内存地址,释放后指针要及时置 NULL ,避免野指针,如 free(p); p = NULL; 。

(三)内存泄漏问题

若只申请堆内存(用 malloc 等 ),使用完不释放(调用 free ),会导致内存泄漏,程序持续运行时可用内存越来越少,最终可能引发性能问题甚至程序崩溃,务必养成申请后及时释放的习惯。

五、位运算符:高效操作二进制位

(一)常用运算符及含义

&按位与:与0得0,| 按位或:或1置1
^异或:相同为0,相异为1
<<左移:让数据变大,等价于 * 2^n
>>右移:让数据缩小,等价于 / 2^n
^异或:可以实现不使用第三方变量完成两个数的交换

 

(二)优先级与应用场景

位运算符优先级低于算术、关系等运算符,使用时注意结合括号。在操作硬件寄存器(如设置某一位控制硬件功能 )、数据压缩存储、简单加密等场景常用,比如将一个数的第 n 位置 1 ,可 num |= (1 << n); ;将第 n 位清零,可 num &= ~(1 << n); 。

掌握这些知识,能让我们在 C 语言开发中更灵活处理复杂数据、合理管理内存,写出高效且结构清晰的代码。后续还可结合实际项目,不断深化对它们的运用,提升编程能力 。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值