單鏈表的9中運算(有頭結點)[考研重點]

說明

1.有頭結點的單鏈表的9中運算;

2.因爲網上的寫法與書上的多少有點兒出入,所以我就自己寫了一遍常用的9中運算,如果想要不帶頭結點的運算,你可以在相應的運算中加一個 if 判斷,然後把沒有頭結點的情況列進去就行啦!

代碼

#include<stdio.h>
#include<stdlib.h>

#define OK 1
#define ERROR 0

typedef int Status;
typedef int ElemType;

typedef struct LNode
{
    ElemType data;
    LNode *next;
}LNode, *LinkList;

Status InitList(LinkList &L)
{   // 初始化
    L = (LinkList)malloc(sizeof(ElemType));
    if(!L) return ERROR;  // 分配內存失敗
    L->next = NULL;

    return OK;
}//InitList

Status DispList(LinkList &L)
{   // 打印單鏈表
    LinkList p = L;
    p = p->next;
    while(p)
    {
        printf("%d\t", p->data);
        p = p->next;
    }
    return OK;
}//DispList

Status ListLength(LinkList &L)
{   // 獲取單鏈表的長度
    int i = 0;
    LinkList p = L;
    while(p->next)
    {
        p = p->next;
        i ++;
    }
    return i;
}//ListLength

Status GetElem(LinkList &L, int i, LinkList e)
{   // 用 e 返回 L 中第 i 個元素的值
    LinkList p = L;
    for(int j = 0; j < i; j++)
        p = p->next;
    e = p;
    return e->data;
}//GetElem

Status ListInsert(LinkList &L, int i, int e)
{   // 在表 L 的第 i 個元素之前(邏輯位序與物理位序差 1 )插入新元素 e
    LinkList p, temp, x;
    int j = 0;
    p = L;
    if(i < 1 || i > ListLength(L)-1) return ERROR;  // 非法插入
    while(p && j < i-1)
    {    
        p = p->next;
        j++;
    }
    temp = (LinkList)malloc(sizeof(LNode));
    if(!temp) return ERROR;

    temp->data = e;
    temp->next = p->next;
    p->next = temp;
    return OK;
}//ListInsert

Status DestroyList(LinkList &L)
{   // 銷燬單鏈表
    LinkList p;
    while(L)    // 如果單純的 free(L) 就只是釋放了頭結點的內存空間,會造成內存碎片
    {
        p = L->next;
        free(L);
        L = p;
    }

    return OK;
}//Destroy

Status ListEmpty(LinkList &L)
{   // 判斷單鏈表是否爲空
    return L->next == NULL;
}//ListEmpty

Status LocateElem(LinkList &L, ElemType e)
{   // 返回 L 中第一個與 e 相等的元素的邏輯位序
    int i = 0;
    LinkList p;
    p = L->next;
    while(p->data != e)
    { 
        if(p)
        {
            printf("\n該元素不在本鏈表中!\n");
            return ERROR;
            break;
        }   
        p = p->next;
        i ++;
    }    
    return i;
}//LocateElem

Status ListDelete(LinkList &L, int i, ElemType e)
{   // 刪除表 L 中 第 i 個元素
    // 注:1 <= i <= n
    int j = 0;
    LinkList p, q;
    p = L;
    if(i < 1 || i > ListLength(L)-1) return ERROR;  // 非法插入
    while(p->next && j < i-1)
    {
        p = p->next;
        j++;
    }
    q = p->next;
    p->next = q->next;
    e = q->data;
    free(q);
    printf("\n刪除的元素爲:%d\n", e);
    return OK;
}//ListDelete

int main()
{
    int choice = 1, i, temp;
    LinkList L, e;
    printf("請輸入序號進行相應的操作:\n");
    while(choice != 0)
    {    
        printf("\n1.InitList   2.ListLength   3.DispList   4.GetElem   5.LocateElem \n6.ListInsert   7.ListDelete   8.ListEmpty   9.Destroy   0.exit\n");
        scanf("%d", &choice);
        switch (choice)
        {
            case 1:
                if(InitList(L))
                    printf("\n初始化單鏈表成功!\n");
                break;
            case 2:
                if(ListEmpty(L))
                    printf("\n單鏈表爲空\n");
                else
                    printf("\n單鏈表的長度爲:%d\n", ListLength(L));
                break;
            case 3:
                if(ListEmpty(L))
                    printf("\n單鏈表爲空\n");
                else
                {
                    printf("\n單鏈表爲:\n");
                    DispList(L);
                }
                break;
            case 4:
                if(!ListEmpty(L))
                {
                    printf("\n請輸入想要 get 的元素的邏輯位序:");
                    scanf("%d", &i); 
                    GetElem(L, i, e);
                }
                else
                    printf("\n單鏈表爲空,你在無中生有、暗度陳倉....\n");
                break;
            case 5:
                if(ListEmpty(L))
                    printf("\n單鏈表爲空,你找個錘兒!\n");
                else
                {
                    printf("\n請輸入想要查找的元素:\n");
                    scanf("%d", &temp);
                    LocateElem(L, temp);
                }
                break;
            case 6:
                printf("\n請輸入想要插入的位置和想要插入的元素(中間用空格隔開):\n");
                scanf("%d %d", &i, &temp);
                // scanf("%d", &temp);
                if(ListInsert(L, i, temp))
                    printf("\n插入成功!\n");
                else
                    printf("\n插入失敗!\n");
                break;
            case 7:
                if(ListEmpty(L))
                    printf("\n單鏈表爲空!\n");
                else
                { 
                    printf("\n請輸入想要刪除的元素的位置:\n");
                    scanf("%d", &i);
                    ListDelete(L, i, temp);
                }
                break;
            case 8:
                if(ListEmpty(L))
                    printf("\n單鏈表爲空!\n");
                else
                    printf("\n有內容!不爲空!\n");
                break;
            case 9:
                if(DestroyList(L))
                    printf("\n銷燬成功\n");
                else
                    printf("\n銷燬失敗!\n");
                break;
            case 0:
                choice = 0;
                break;
            default:
                printf("\n程序出錯!\n");
                break;
        }
    }
    DestroyList(L);   // 養成用完就銷燬的好習慣,不給電腦增加負擔!
    return 0;
}

運行結果示意圖就不貼出來啦,因爲用的不是 CreateList() 函數生成的單鏈表,而是 ListInsert() 函數一個一個插入的,這樣的話結果會比較長,我也不會截取長圖....抱歉....

THE END!

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章