1. 程式人生 > >C 知識點(4)

C 知識點(4)

連結串列實現

記憶體零碎資料的有效組織。比如,當我們用 malloc 來進行記憶體申請的時候,當記憶體足夠,而由於碎片太多,沒有連續記憶體時,只能以申請失敗而告終,而用連結串列這種資料結 構來組織資料,就可以解決上類問題。

連結串列原理的實現(靜態連結串列)

#include <stdio.h>
typedef struct node
{
    int data;
    struct node * next;
}Node;

int main(void)
{
    Node a;
    Node b;
    Node c;
    a.data = 10;
    b.data = 20
; c.data = 30; a.next = &b; b.next = &c; c.next = NULL; Node * head = &a; while (head != NULL) { printf("data = %d\n",head->data); head = head->next; } return 0; }

執行結果

data = 10
data = 20
data = 30

動態連結串列

靜態連結串列的意義不是很大,主要原因,資料儲存在棧上,棧的儲存空間有限,不能動態分配。所空連結串列要實現儲存的自由,要動態的申請堆裡的空間。

定義結構體表示節點

typedef struct node
{
    int data;
    struct node * next;
}Node;

頭插法建立連結串列

// 頭插法建立連結串列
Node *createList_h()
{
    Node * head = (Node *)malloc(sizeof(Node));
    head->next = NULL;
    Node * cur;
    int temp;
    while (1) {
        scanf("%d",&temp);
        if(temp == 0
) break; cur = (Node *)malloc(sizeof(Node)); cur->data = temp; cur->next = head->next; head->next = cur; } return head; }

尾插法建立連結串列

//尾插法建立連結串列
Node * createList_l()
{
    Node * head = (Node*)malloc(sizeof(Node));
    head->next = NULL;
    Node *pre = head;
    Node *last;
    int data;
    scanf("%d",&data);
    while (data) {
        last = (Node*)malloc(sizeof(Node));
        last->data = data;
        last->next = NULL;
        pre->next = last;
        pre = last;

        scanf("%d",&data);
    }
    return head;
}

連結串列遍歷

//連結串列遍歷
void traverseList(Node *head)
{
    head = head->next;
    while (head !=NULL) {
        printf("%d\n",head->data);
        head = head->next;
    }
}

求連結串列長度

// 求連結串列長度
int lenList(Node * head)
{
    int len = 0;
    head = head->next;
    while (head) {
        len++;
        head = head->next;
    }
    return len;
}

插入

//插入
void insertList(Node * head,int inserData)
{
    Node * cur = (Node *)malloc(sizeof(Node));
    cur->data = inserData;
    cur->next = head->next;
    head->next = cur;
}

查詢

//查詢
Node *searchList(Node *head,int find)
{
    head = head->next;
    while (head) {
        if(head->data == find)
            break;
        head = head->next;
    }
    return head;
}

刪除

//刪除
void deleteList(Node *head , Node *del)
{
    while (head->next != del)
    head = head->next;
    head->next = del->next;
    free(del);
}

排序 換值

//排序 換值
void sortList(Node * head, int len)
{
    for (int i=0; i<len-1; i++)
    {
        Node * cur = head->next;
        for (int j=0; j<len-1; j++)
        {
            if(cur->data>cur->next->data)
            {
                int tmp = cur->data;
                cur->data = cur->next->data;
                cur->next->data = tmp;
            }
            cur = cur->next;
        }
    }
}

排序 換指標

//排序 換指標
void sortHeadByPtr(Node *head,int len)
{
    Node * subHead,*p,*q,*tmp;
    int i,j;
    for (i=0; i<len-1; i++)
    {
        subHead = head;
        p = head->next;
        q = p->next;
        for (j = 0; j<len-1; j++)
        {
            if(p->data>q->data)
            {
                subHead->next = p->next;
                p->next = q->next;
                q->next = p;

                tmp = p;
                p = q;
                q = tmp;
            }
            subHead = subHead->next;
            p = p->next;
            q = q->next;
        }
    }
}

連結串列反轉

//連結串列反轉
void reverseList(Node * head)
{
    Node* p = head ->next,*q;
    head->next = NULL;

    while (p != NULL) {
        q = p->next;
        p->next = head->next;
        head->next = p;
        p = q;
    }
}

測試

int main(void)
{
//    Node *head = createList_l();
    Node *head = createList_h();
    traverseList(head)
    printf("the length of List is %d\n",lenList(head));
    insertList(head, 666);
    traverseList(head);
    Node *pfind = searchList(head, 666);
    if(pfind == NULL)
        printf("find none\n");
    else
    {
        printf("your find in list %p\n",pfind);
        deleteList(head, pfind);
    }

    traverseList(head);
//    sortList(head, lenList(head));
    sortHeadByPtr(head, lenList(head));
    printf("the List after sort is:\n");
    traverseList(head);
    reverseList(head);
    traverseList(head);
    destroyList(head);
    printf("after destory!!\n");
    traverseList(head);
    return 0;
}