1. 程式人生 > >C語言--結構體學習總結

C語言--結構體學習總結

結構體

一種能包含多種資料型別,存在變數間聯絡,並保持資料獨立的神奇型別。


1.結構佈局

* 結構佈局即建立一個模版。之後使用這個模版(自定義多個變數),快捷建立一組變數。
*例項:學生資訊管理系統,將一個學生的資訊儲存在一個結構體中,將所有的結構體放到一個結構體中。 
struct book{
    char title[15];
    char author[30];
    int num;
    float value;
    };//注意這裡還有一個分號
*book為一個結構標記,即所做結構佈局的名字。後期定義可直接用book代替這些變數型別。

ps:1.結構佈局只是告訴系統,需要配置一組什麼型別的變數塊,實際作用相當於定義了一種新的變數型別
ps:2.結構佈局時不佔用系統記憶體,只有結構被定義時,才會分配記憶體
ps:3.結構佈局不能被初始化,它只是一個數據型別
ps:4.結構佈局要定義在主函式外部,這樣其他的函式才能,獲取對應型別,分配相應記憶體


2.宣告與定義

struct {
    char title[15];
    char author[30];
    int num;
    float value;
    }library;//基礎定義
struct
book{ char title[15]; char author[30]; int num; float value; }library;//完整定義
struct book library;//簡化定義

ps:1.如需多次使用模版,需要使用標記形式


3.初始化

struct book library={
    "abppel","shdjhsk",
    35,
    15.23};//按順序依次定義
struct book library={
    .title="abppel"
, "shdjhsk",//對於緊跟其後的值,可以省略名稱 .valude=15.23};//選擇特定物件定義

ps:1.初始化的值必須是常量
ps:2.每個部分用逗號隔開,行數隨意選擇
ps:3.結構的初始化器,可以選擇特定的部分進行初始化


4.訪問

    printf("%s",library.author);
    printf("%d",library.num);

ps:1.使用成員運算子(.),進行對結構成員的訪問。


5.結構陣列

  • 由結構體為元素,構成的數字
struct book{
    char title[15];
    char author[30];
    int num;
    float value;
    };

int main(void)
{
    struct book library[50];//建立結構的陣列


    int i;
    for(i=0 ; i<50 ; i++)//迴圈一次,輸入一個結構體
    {
        scanf(*****);
        scanf(*****);
        scanf(*****);//對應型別的輸入
    }


    printf("%d",library[34].num);//訪問與輸出

    return 0;
}

ps:1.陣列名稱,代表陣列中第一個結構體的地址。
ps:2.結構陣列在記憶體中也是連續儲存的。


6.巢狀結構

  • 結構體套結構體
struct name{
    char firstname[10];
    char lastname[10];
    };

struct people{
    int age;
    char country[25];
    struct name mz;
    };

int main(void)
{
    struct people a = {
        19,"England",
        {"Tom","Humphrey"}
        };

    printf("first name is %s.",people.mz.firstname);
    return 0;
}

ps:1.注意巢狀結構體訪問時的順序—由大到小
ps:2.訪問時要使用變數名,而不是型別名


7.指向結構的指標

struct name{
    char firstname[10];
    char lastname[10];
    };

struct people{
    int age;
    char country[25];
    struct name mz;
    };

int main(void)
{
    struct people* x;//宣告一個結構體指標

    struct people a = {
        19,"England",
        {"Tom","Humphrey"}
        };

    x = &a;//指標指向a結構體

    printf("first name is %s.",(*x).mz.firstname);
    printf("first name is %s.",x->mz.firstname);
    return 0;
}

ps:1.指標的優勢,提高程式效率
ps:2.結構陣列在記憶體中也是連續儲存的,可以使用指標的運算
ps:3.只有當使用指標時,才能用 ->符號


8.結構體與函式

#include<stdio.h>
#include<string.h>
struct name{
    char firstname[10];
    char lastname[10];
};

struct people{
    int age;
    char country[25];
    struct name mz;
};


struct people hs(struct people );//宣告兩個函式  函式可以傳遞
void zz(struct people *);

int main(void)
{
    struct people* x;
    struct people c;
    struct people a = {
        19, "England",
        { "Tom", "Humphrey" }
    };

    x = &a;
    zz(x);
    c = hs(a);//結構體可以相互轉換

    printf("%s", c.country);
    printf("%s", c.mz.firstname);

    return 0;
}
struct people hs(struct people b)
{
    strcpy(b.country,"China");//使用string.h進行字串變更
    strcpy(b.mz.firstname, "Jam");

    return b;
}

void zz(struct people * x)
{
    printf("first name is %s.", x->mz.firstname);
}

ps:1.結構體(結構體陣列)可以作為引數,在函式間傳遞
ps:2.結構體中字串需要用string.h進行變更
ps:3.結構體可以相互賦值
ps:4.函式引數使用指標或結構體本身各有優缺點

分類 指標 結構體
優勢 響應迅速,效率高 清晰明瞭,符合思維
缺陷 資料可能意外修改 佔用較大記憶體

ps:5.建議const + 指標,作為引數進行傳遞


9.匿名結構

struct person {
    int id;
    struct { char first[10]; char second[10]; };//匿名結構
};

int main(void)
{
    struct person std = { 7632298, { "jok", "Humphrey" } };
    printf("%s", std.second);//呼叫匿名內容

    return 0;

}

ps: 匿名結構在結構體的巢狀中使用,內部的結構體可以不加結構標記,在呼叫中可以直接呼叫


10.typedef

  • 用途一:
    定義一種型別的別名,而不只是簡單的巨集替換。可以用作同時宣告指標型的多個物件
char* pa, pb; // 這多數不符合我們的意圖.
// 它只聲明瞭一個指向字元變數的指標,和一個字元變數;

typedef char* PCHAR; // 一般用大寫
PCHAR pa, pb; // 可行,同時聲明瞭兩個指向字元變數的指標

char *pa, *pb;
//雖然:也可行,但相對來說沒有用typedef的形式直觀,尤其在需要大量指標的地方,typedef的方式更省事。
  • 用途二:
    用在舊的C的程式碼中(具體多舊沒有查),幫助struct。
struct tagPOINT1  
{  
    int x;  
    int y;  
};  
struct tagPOINT1 p1;   


typedef struct tagPOINT  
{  
    int x;  
    int y;  
}POINT;  
POINT p1; // 這樣就比原來的方式少寫了一個struct,比較省事,尤其在大量使用的時候  


  • 用途三:
    為複雜的宣告定義一個新的簡單的別名。

ps:用typedef 宣告的量,其實相當於一個新的資料型別