Day 14.15 关键字与内存管理

关键字1.struct

一、结构体概念

     前面我们了解了数组Array),它是一组具有相同类型的数据的集合。但在实际的编程过程中,我们往往还需要一组类型不同的数据,例如对于学生信息登记表,姓名为字符串,学号为整数,年龄为整数,所在的学习小组为字符,成绩为小数,因为数据类型不同,显然不能用一个数组来存放。在C语言中,可以使用结构体(Struct)来存放一组不同类型的数据。结构体的定义形式为:

struct 结构体名{

    结构体所包含的变量或数组

};

     结构体是一种集合,它里面包含了多个变量或数组,它们的类型可以相同,也可以不同,每个这样的变量或数组都称为结构体的成员(Member)。请看下面的一个例子:

 struct stu{

    char *name;  //姓名

    int num;  //学号

    int age;  //年龄

    char group;  //所在学习小组

    float score;  //成绩

};

      stu 为结构体名它包含了 5 个成员分别是 namenumagegroupscore。结构体成员的定义方式与变量和数组的定义方式相同,只是不能初始化。注意大括号后面的分号;不能少,这是一条完整的语句。结构体也是一种数据类型它由程序员自己定义,可以包含多个其他类型的数据。像 intfloatchar 等是由C语言本身提供的数据类型,不能再进行分拆,我们称之为基本数据类型;而结构体可以包含多个基本类型的数据,也可以包含其他的结构体,我们将它称为混合数据类型

 

二、结构体的三种定义方式:

 结构体变量

既然结构体是一种数据类型,那么就可以用它来定义变量。例如:

struct stu stu1, stu2;

定义了两个变量 stu1 stu2,它们都是 stu 类型,都由 5 个成员组成。注意关键字struct不能少。

你也可以在定义结构体的同时定义结构体变量:

struct stu{

 } stu1, stu2;

将变量放在结构体定义的最后即可。

如果只需要 stu1stu2 两个变量后面不需要再使用结构体名定义其他变量那么在定义时也可以不给出结构体名如下所示

 struct{  //没有写 stu

} stu1, stu2;

这样做书写简单,但是因为没有结构体名,后面就没法用该结构体定义新的变量

成员的获取和赋值

结构体和数组类似,也是一组数据的集合,整体使用没有太大的意义。数组使用下标[ ]获取单个元素,结构体使用点号 . 获取单个成员。获取结构体成员的一般格式为:

结构体变量名.成员名;

赋值方式:

1、使用逐一赋值的方式对结构体各元素进行赋值。(2

2、在定义时整体赋值

注:整体赋值仅限于定义结构体变量的时候,在使用过程中只能对成员逐一赋值,这和数组的赋值非常类似。

结构体数组

所谓结构体数组,是指数组中的每个元素都是一个结构体。在实际应用中,结构体数组常被用来表示一个拥有相同数据结构的群体,比如一个班的学生、一个车间的职工等。

 

定义结构体数组和定义结构体变量的方式类似,请看下面的例子:

 struct stu{

    char *name;  //姓名

    int num;  //学号

    int age;  //年龄

    char group;  //所在小组

    float score;  //成绩

}class[5];

表示一个班级有5个学生。

 

结构体数组在定义的同时也可以初始化,例如:

struct stu{

    char *name;  //姓名

    int num;  //学号

    int age;  //年龄

    char group;  //所在小组

    float score;  //成绩

}class[5] = {

    {"Li ping", 5, 18, 'C', 145.0},

    {"Zhang ping", 4, 19, 'A', 130.5},

    {"He fang", 1, 18, 'A', 148.5},

    {"Cheng ling", 2, 17, 'F', 139.0},

    {"Wang ming", 3, 17, 'B', 144.5}

};

当对数组中全部元素赋值时,也可不给出数组长度

 

结构体数组的使用也很简单例如获取 Wang ming 的成绩

class[4].score;

修改 Li ping 的学习小组

class[0].group = 'B';

结构体和指针

一、结构体指针含义:

指针也可以指向一个结构体,定义的形式一般为:

struct 结构体名 *变量名;

下面是一个定义结构体指针的实例:

struct stu{

} stu1 = { "Tom", 12, 18, 'A', 136.5 };

struct stu *pstu = &stu1;

 

注意:结构体变量名和数组名不同,数组名在表达式中会被转换为数组指针,而结构体变量名不会,无论在任何表达式中它表示的都是整个集合本身,要想取得结构体变量的地址,必须在前面加&,所以给 pstu 赋值只能写作:

struct stu *pstu = &stu1;

而不能写作:

struct stu *pstu = stu1;

 

2.typedef

为了编码方便,C语言允许为一个数据类型起一个新的别名。

使用关键字 typedef 可以为类型起一个新的别名,语法格式为:

typedef  oldName  newName;

例如

1typedef int INTEGER;

INTEGER a, b;等效于int a, b;           5

typedef 还可以给数组、指针、结构体等类型定义别名。

2typedef char ARRAY20[20];

ARRAY20 a1, a2, s1, s2;它等价于char a1[20], a2[20], s1[20], s2[20];

3、为结构体类型定义别名:

typedef struct stu{

    char name[20];

    int age;

    char sex;

} STU;

STU body1,body2;它等价于struct stu body1, body2;

4、为指针类型定义别名:

typedef int (*PTR_TO_ARR)[4];表示 PTR_TO_ARR 是类型int * [4]的别名它是一个二维数组指针类型。

PTR_TO_ARR p1, p2;

5、为函数指针类型定义别名:

typedef int (*PTR_TO_FUNC)(int, int);

PTR_TO_FUNC pfunc;

Typedefdefine的区别

typedef 在表现上有时候类似于 #define但它和宏替换之间存在一个关键性的区别。正确思考这个问题的方法就是 typedef 看成一种彻底的封装类型,声明之后不能再往里面增加别的东西。

 

1) 可以使用其他类型说明符对宏类型名进行扩展,但对 typedef 所定义的类型名却不能这样做。例如:

#define INTERGE int

unsigned INTERGE n;  //没问题

 

typedef int INTERGE;

unsigned INTERGE n;  //错误不能在 INTERGE 前面添加 unsigned

 

2) 连续定义几个变量的时候typedef 能够保证定义的所有变量均为同一类型 #define 则无法保证。例如

#define PTR_INT int *

PTR_INT p1, p2;

经过宏替换以后,第二行变为:

int *p1, p2;

这使得 p1p2 成为不同的类型p1 是指向 int 类型的指针p2 int 类型。

 

相反,在下面的代码中:

typedef int * PTR_INT

PTR_INT p1, p2;

p1p2 类型相同,它们都是指向 int 类型的指针。

内存管理

Malloc函数

malloc 函数的原型

 (void *)malloc(int size)

         malloc 函数的返回值是一个 void 类型的指针参数为 int 类型数据即申请分配的内存大小单位是字节byte内存分配成功之后,malloc 函数返回这块内存的首地址。需要一个指针来接收这个地址。但是由于函数的返回值是 void *类型的,所以必须强制转换成你所接收的类型。

比如

char *p = (char *)malloc(100);

     在堆上分配了 100 个字节内存返回这块内存的首地址把地址强制转换成 char *类型后赋给 char *类型的指针变量 p。同时告诉我们这块内存将用来存储 char 类型的数据。也就是说你只能通过指针变量 p 来操作这块内存

 

注意: 1malloc 函数申请内存有不成功的可能,在使用指向这块内存的指针时,必须用 if( NULL != p )语句来验证内存确实分配成功了。

 2、调用之前加上头文件   #include<stdlib.h>      6   mallocrealloccallocfree

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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值