Skip to content

C 语言入门(八)

前言

呀呀呀!C 语言完结篇🤗

八、struct 结构体

8.1 struct 关键字

“建”你所“建”😋

C 语言中除了内置的数据类型,还提供了struct关键字用来自定义数据类型。

c
// 定义了一个动物数据类型,包含两个成员属性猫和狗。
struct Animal {
  int cat;
  int dog;
};
// 使用
struct Animal a1;

a1.cat = 2;
a1.dog = 3;

//声明
struct Book {
  char title[500];
  char author[100];
  float value;
} b1;

//声明
struct {
  char title[500];
  char author[100];
  float value;
} b1,b2;

TIP

结构体使用点运算符(.)获取属性;结构体指针使用箭头运算符(->)获取属性。

成员赋值

结构体的几种不同赋值方式

c
//大括号赋值
struct Animal a1 = {2, 3};

//声明赋值
struct {
  char title[500];
  char author[100];
  float value;
} b1={"a", "b", 10.0};

//声明多赋值
struct {
  char title[500];
  char author[100];
  float value;
} b1={"a", "b", 10.0},
  b2={"c", "d", 5.0};

8.2 struct 数组

struct 结构也可以作为数组成员。

c
struct Animal num[10];

num[0].cat = 2;
num[0].dog = 3;

struct 结构占用的存储空间,是最大内存占用属性的存储空间的倍数,其他属性会添加会对齐空间。这样可以提高读写效率。

这里有关计组的数据边界对齐问题了,就不细讲了🤔

struct 的复制

跟数组的复制不一样,struct 变量可以使用赋值运算符复制给另一个变量,这时会生成一个全新的副本。

c
struct Person {
    char name[50];
    int age;
};
struct Person p1 = {"xiao", 18};
struct Person p2 = p1;

8.3 struct 指针

结构体指针

如果你学过数据结构,你可能看过许多结构体中有指针的身影。结构体指针在数据结构中有大量运用。

提示

结构体使用点运算符(.)获取属性;结构体指针使用箭头运算符(->)获取属性。

c
typedef int ElemType;
typedef struct LNode {
    ElemType data;
    struct LNode* next;
} LNode, *LinkNode;

// 头插法创建链表
void CreateListF(LinkNode* L, ElemType a[], int n) {
    LinkNode s;
    *L = (LinkNode)malloc(sizeof(LNode));
    (*L)->next = NULL;
    for (int i = 0; i < n; i++) {
        s = (LinkNode)malloc(sizeof(LNode));
        s->data = a[i];
        s->next = (*L)->next;
        (*L)->next = s;
    }
}

// 尾插法创建链表
void CreateListR(LinkNode* L, ElemType a[], int n) {
    LinkNode s, r;
    *L = (LinkNode)malloc(sizeof(LNode));
    r = *L;
    for (int i = 0; i < n; i++) {
        s = (LinkNode)malloc(sizeof(LNode));
        s->data = a[i];
        r->next = s;
        r = s;
    }
    r->next = NULL;
}

// 销毁单链表
void DestroyList(LinkNode* L) {
    LinkNode ptr = *L, p = (*L)->next;
    while (p != NULL) {
        free(ptr);
        ptr = p;
        p = ptr->next;
    }
    free(ptr);
}

上面是一个单链表,我就不就行讲解了。如果你有数据结构的基础,想必你比我懂。我来讲讲结构体指针获取属性,结构体使用点运算符获取属性而结构体指针使用箭头运算符获取属性。其实箭头运算符算一个”语法糖“,它简化了(*ptr).data的写法为ptr->data

8.4 struct 的嵌套

struct 结构的成员可以是另一个 struct 结构,实现复杂的复合结构。

c
struct Animal {
  int cat;
  int dog;
};

struct Biology {
  struct Animal a1;
  int b1;
};

成员赋值

c
// 写法一
struct Biology bi = {{2,3},4};

// 写法二
struct Animal a1 = {2,3};
struct Biology bi = {a1,4};

// 写法三
struct Biology bi = {
  .b1=4
  .a1={2,3}
};

// 写法四
struct Biology bi = {
  .b1=4,
  .a1.cat=2,
  .a1.dog=3
};

自我嵌套

struct 结构内部不仅可以引用其他结构,还可以自我引用。

c
struct node {
  int data;
  struct node* next;
};

上面的node结构的next属性,就是指向另一个node实例的指针。

8.5 typedef 命令

typedef命令用来为某个类型起别名,以简化声明等等。

c
typedef type name;
// `type`代表类型名,`name`代表别名。

// 多别名
typedef int ab, cd, ef;
// 指针别名
typedef int* intptr;
// 数组别名
typedef int arr[5];
// 函数别名
typedef signed char (*fp)(void);
// 结构体别名
typedef struct Animal {
  int cat;
  int dog;
} Animal;

写在最后

欢迎来到计算机的世界,Hello,World!🎉

到此 C 语言入门就到此完结了🎉🎉🎉,后续可能会有“番外”,尽请期待。

如有转载或 CV 请标注本站原文地址