单链表的的建立、插入、删除和查找(附完整代码)

1.单链表的定义

          线性表的链式存储又称单链表,它是指通过一组任意的存储单元来存储线性表中的数据元素。为了建立数据元素之间的线性关系,对每个链表结点,除存放元素自身的信息之外,还需要存放一个指向其后继的指针。

2.单链表的基本操作

2.1单链表的建立

2.1.1头插法建立单链表

       该方法从一个空表开始,生成新结点,并将读取到的数据存放到新结点的数据域中,然后将新结点插入到当前链表的表头,即头结点之后。

// 头插法建立单链表 
Node* createListHead(int arr[], int n) {
    Node* head = NULL;
    for (int i = 0; i <n; i++) {
        Node* newNode = (Node*)malloc(sizeof(Node));
        newNode->data = arr[i];
        newNode->next = head;
        head = newNode;
    }
    return head;
}
2..1.2尾插法建立单链表

      该方法将新结点插入到当前链表的表尾,为此必须增加一个尾指针 ,使其始终指向当前链表的尾结点。

// 尾插法建立单链表 
Node* createListTail(int arr[], int n) {
    Node* head = NULL;
    Node* tail = NULL;
    for (int i = 0; i < n; i++) {
        Node* newNode = (Node*)malloc(sizeof(Node));
        newNode->data = arr[i];
        newNode->next = NULL;
        if (head == NULL) {
            head = newNode;
            tail = newNode;
        } else {
            tail->next = newNode;
            tail = newNode;
        }
    }
    return head;
}

2.2.删除单链表节点

       删除结点操作是将单链表的第i个结点删除。先检查删除位置的合法性,然后查找表中第i-1个结点,即被删结点的前驱,再删除第i个结点。

// 删除单链表节点
void deleteByIndex(Node** head, int index) {
    if (*head == NULL) {
        return;
    }

    Node* current = *head;//如果要删除的是头结点 
    if (index == 0) {
        *head = current->next;
        free(current);
        return;
    }

    for (int i = 0; current != NULL && i < index - 1; i++) {//删除的不是头结点 
        current = current->next;
    }

    if (current == NULL || current->next == NULL) {
        return;
    }

    Node* temp = current->next;
    current->next = temp->next;
    free(temp);
}

2.3.插入单链表节点

        插入结点操作将值为x的新结点插入到单链表的第i个位置。先检查插入位置的合法性,然后找到待插入位置的前驱,即第i-1个结点,再在其后插入。

// 单链表中插入节点
void insertByIndex(Node** head, int index, int value) {
	//创建一个新节点 
    Node* newNode = (Node*)malloc(sizeof(Node));
    newNode->data = value;
    newNode->next = NULL;

    if (*head == NULL || index == 0) {
        newNode->next = *head;
        *head = newNode;
        return;
    }

    Node* current = *head;
    for (int i = 0; current != NULL && i < index - 1; i++) {
        current = current->next;
    }

    if (current == NULL) {
        free(newNode);
        return;
    }

    newNode->next = current->next;
    current->next = newNode;
}

2.4.查找到单链表节点

2.4.1按值查找

       从单链表的第一个结点开始,从前往后依次比较表中各结点的数据域,若某结点的 data 域等于给定值e,则返回该结点的指针;若整个单链表中没有这样的结点,则返回NULL。

//按值查找点
Node* findByValue(Node* head, int value) {
    Node* current = head;
    while (current != NULL) {
        if (current->data == value) {
            return current;
        }
        current = current->next;
    }
    return NULL;
}
2.4.2按位查找

        从单链表的第一个结点开始,沿着 next域从前往后依次搜索,直到找到第i个结点为止,
则返回该结点的指针;若i小于单链表的表长,则返回NULL。

// 按位查找
Node* findByIndex(Node* head, int index) {
    Node* current = head;
    for (int i = 0; current != NULL && i < index; i++) {
        current = current->next;
    }
    return current;

2.5.main主函数

int main() {
    int n;
    printf("请输入节点数量: ");
    scanf("%d", &n);
    int arr[n];
    printf("请输入节点数据: ");
    for (int i = 0; i < n; i++) {
        scanf("%d", &arr[i]);
    }

    // 创建单链表
    Node* head = createListTail(arr, n);
    printf("初始链表: ");
    printList(head);

    // 插入和删除测试
    int deleteIndex, insertIndex, findIndex;

    printf("请输入要删除的位置(0为头节点): ");
    scanf("%d", &deleteIndex);
    deleteByIndex(&head, deleteIndex);
    printf("删除位置 %d 后的链表: ", deleteIndex);
    printList(head);

    printf("请输入要插入的位置(0为头节点): ");
    scanf("%d", &insertIndex);
    printf("请输入要插入的值: ");
    int insertValue;
    scanf("%d", &insertValue);
    insertByIndex(&head, insertIndex, insertValue);
    printf("插入位置 %d 后的链表: ", insertIndex);
    printList(head);

    printf("请输入要查找的位置(0为头节点): ");
    scanf("%d", &findIndex);
    Node* foundNode = findByIndex(head, findIndex);
    if (foundNode) {
        printf("找到索引 %d 的节点: %d\n", findIndex, foundNode->data);
    } else {
        printf("未找到索引 %d 的节点\n", findIndex);
    }

    // 按值查找
    printf("请输入要查找的值: ");
    int findValue;
    scanf("%d", &findValue);
    foundNode = findByValue(head, findValue);
    if (foundNode) {
        printf("找到值 %d 的节点: %d\n", findValue, foundNode->data);
    } else {
        printf("未找到值 %d 的节点\n", findValue);
    }

    // 清理链表
    while (head != NULL) {
        Node* temp = head;
        head = head->next;
        free(temp);
    }

    return 0;
}

3.运行结果

3.1单链表的建立

3.2删除节点

3.3插入节点

3.4查找节点

3.4.1按值查找

3.4.2按位查找

4.完整代码

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

// 定义单链表节点结构体
typedef struct Node {
    int data;
    struct Node* next;
} Node;
 
// 头插法建立单链表 
Node* createListHead(int arr[], int n) {
    Node* head = NULL;
    for (int i = n - 1; i >= 0; i--) {
        Node* newNode = (Node*)malloc(sizeof(Node));
        newNode->data = arr[i];
        newNode->next = head;
        head = newNode;
    }
    return head;
}

// 尾插法建立单链表 
Node* createListTail(int arr[], int n) {
    Node* head = NULL;
    Node* tail = NULL;
    for (int i = 0; i < n; i++) {
        Node* newNode = (Node*)malloc(sizeof(Node));
        newNode->data = arr[i];
        newNode->next = NULL;
        if (head == NULL) {
            head = newNode;
            tail = newNode;
        } else {
            tail->next = newNode;
            tail = newNode;
        }
    }
    return head;
}

// 打印单链表
void printList(Node* head) {
    Node* current = head;
    while (current != NULL) {
        printf("%d ", current->data);
        current = current->next;
    }
    printf("\n");
}

// 删除单链表节点
void deleteByIndex(Node** head, int index) {
    if (*head == NULL) {
        return;
    }

    Node* current = *head;//如果要删除的是头结点 
    if (index == 0) {
        *head = current->next;
        free(current);
        return;
    }

    for (int i = 0; current != NULL && i < index - 1; i++) {//删除的不是头结点 
        current = current->next;
    }

    if (current == NULL || current->next == NULL) {
        return;
    }

    Node* temp = current->next;
    current->next = temp->next;
    free(temp);
}

// 单链表中插入节点
void insertByIndex(Node** head, int index, int value) {
	//创建一个新节点 
    Node* newNode = (Node*)malloc(sizeof(Node));
    newNode->data = value;
    newNode->next = NULL;

    if (*head == NULL || index == 0) {
        newNode->next = *head;
        *head = newNode;
        return;
    }

    Node* current = *head;
    for (int i = 0; current != NULL && i < index - 1; i++) {
        current = current->next;
    }

    if (current == NULL) {
        free(newNode);
        return;
    }

    newNode->next = current->next;
    current->next = newNode;
}

// 按位查找
Node* findByIndex(Node* head, int index) {
    Node* current = head;
    for (int i = 0; current != NULL && i < index; i++) {
        current = current->next;
    }
    return current;
}

//按值查找点
Node* findByValue(Node* head, int value) {
    Node* current = head;
    while (current != NULL) {
        if (current->data == value) {
            return current;
        }
        current = current->next;
    }
    return NULL;
}

int main() {
    int n;
    printf("请输入节点数量: ");
    scanf("%d", &n);
    int arr[n];
    printf("请输入节点数据: ");
    for (int i = 0; i < n; i++) {
        scanf("%d", &arr[i]);
    }

    // 创建单链表
    Node* head = createListTail(arr, n);
    printf("初始链表: ");
    printList(head);

    // 插入和删除测试
    int deleteIndex, insertIndex, findIndex;

    printf("请输入要删除的位置(0为头节点): ");
    scanf("%d", &deleteIndex);
    deleteByIndex(&head, deleteIndex);
    printf("删除位置 %d 后的链表: ", deleteIndex);
    printList(head);

    printf("请输入要插入的位置(0为头节点): ");
    scanf("%d", &insertIndex);
    printf("请输入要插入的值: ");
    int insertValue;
    scanf("%d", &insertValue);
    insertByIndex(&head, insertIndex, insertValue);
    printf("插入位置 %d 后的链表: ", insertIndex);
    printList(head);

    printf("请输入要查找的位置(0为头节点): ");
    scanf("%d", &findIndex);
    Node* foundNode = findByIndex(head, findIndex);
    if (foundNode) {
        printf("找到索引 %d 的节点: %d\n", findIndex, foundNode->data);
    } else {
        printf("未找到索引 %d 的节点\n", findIndex);
    }

    // 按值查找
    printf("请输入要查找的值: ");
    int findValue;
    scanf("%d", &findValue);
    foundNode = findByValue(head, findValue);
    if (foundNode) {
        printf("找到值 %d 的节点: %d\n", findValue, foundNode->data);
    } else {
        printf("未找到值 %d 的节点\n", findValue);
    }

    // 清理链表
    while (head != NULL) {
        Node* temp = head;
        head = head->next;
        free(temp);
    }

    return 0;
}

  • 5
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值