【数据结构】单链表的尾插法

news/2024/11/30 6:34:25/

尾插法是一种在链表末尾插入新元素的方法,它的核心思想是保持链表的尾部指针(或称为尾节点),这样可以在常数时间内完成尾部插入操作。尾插法的主要步骤如下:

  1. 创建新节点:首先,根据需要插入的数据创建一个新的链表节点。

  2. 定位尾部:如果是第一次插入,即链表为空,新节点直接成为头节点。如果链表不为空,需要定位到链表的尾部。

  3. 更新尾部:将新节点插入到当前尾部节点的后面,并更新尾部指针(或尾部节点的next指针)以指向新节点。

  4. 维护尾部指针:在插入操作完成后,确保尾部指针指向新的尾部节点。在某些实现中,可能会使用一个额外的指针来始终指向尾部节点,这样可以避免每次插入时都需要遍历链表来找到尾部。

尾插法的优点是插入操作的时间复杂度为O(1),因为不需要遍历链表来找到插入位置,只需要修改尾部节点的next指针。这种方法在实现队列时非常有用,因为队列的入队操作通常需要在尾部插入元素。

在双向链表或循环链表中,尾插法还需要维护额外的指针,例如前驱指针和循环链表的头节点指针,但基本思想是相同的:找到尾部并在其后面插入新节点。

以下是一个使用尾插法在单向链表中插入新元素的C语言示例:

#include <stdio.h>
#include <stdlib.h>// 定义链表节点结构体
typedef struct Node {int data;struct Node* next;
} Node;// 创建一个新的节点
Node* createNode(int data) {Node* newNode = (Node*)malloc(sizeof(Node));if (!newNode) {printf("内存分配失败\n");exit(0);}newNode->data = data;newNode->next = NULL;return newNode;
}// 使用尾插法在链表尾部插入新节点
void insertAtTail(Node** head, int data) {Node* newNode = createNode(data);if (*head == NULL) {// 如果链表为空,新节点成为头节点*head = newNode;return;}Node* current = *head;// 遍历链表直到找到最后一个节点while (current->next != NULL) {current = current->next;}// 将新节点插入到链表的尾部current->next = newNode;
}// 打印链表
void printList(Node* head) {Node* current = head;while (current != NULL) {printf("%d -> ", current->data);current = current->next;}printf("NULL\n");
}// 主函数
int main() {Node* head = NULL;insertAtTail(&head, 1);insertAtTail(&head, 3);insertAtTail(&head, 5);insertAtTail(&head, 7);printf("链表元素: ");printList(head);return 0;
}

在这个例子中,insertAtTail函数接受一个指向头节点的指针的指针,以及要插入的新节点的数据。首先,它创建一个新节点。然后,如果链表为空,新节点成为头节点。如果链表不为空,函数遍历链表直到找到最后一个节点,并将新节点插入到最后一个节点的后面。

printList函数用于打印链表中的所有元素,以验证尾插法是否正确执行。

结语

以上就是尾插法的基本使用,本次代码分享到此结束。

最后的最后,还请大家点点赞,点点关注,谢谢大家!


http://www.ppmy.cn/news/1431243.html

相关文章

lazarus-ide简介

Lazarus是一个集成开发环境&#xff08;IDE&#xff09;&#xff0c;专为使用Free Pascal编译器的Pascal语言设计。它支持快速应用开发&#xff08;RAD&#xff09;&#xff0c;允许开发者创建跨平台的图形用户界面&#xff08;GUI&#xff09;应用程序。以下是关于Lazarus的来…

鸿蒙 harmonyos 线程 并发 总结 async promise Taskpool woker(三)多线程并发 Worker

Worker Worker是与主线程并行的独立线程。创建Worker的线程称之为宿主线程&#xff0c;Worker自身的线程称之为Worker线程。创建Worker传入的url文件在Worker线程中执行&#xff0c;可以处理耗时操作但不可以直接操作UI。 Worker主要作用是为应用程序提供一个多线程的运行环境…

AI检索增强生成引擎-RAGFlow-深度理解知识文档,提取真知灼见

&#x1f4a1; RAGFlow 是什么&#xff1f; RAGFlow是一款基于深度文档理解构建的开源RAG&#xff08;Retrieval-Augmented Generation&#xff09;引擎。RAGFlow个人可以为各种规模的企业及提供一套专业的RAG工作流程&#xff0c;结合针对用户群体的大语言模型&#xff08;LL…

力扣经典150题第三十五题:螺旋矩阵

目录 力扣经典150题第三十五题&#xff1a;螺旋矩阵引言题目详解解题思路代码实现示例演示复杂度分析总结扩展阅读 力扣经典150题第三十五题&#xff1a;螺旋矩阵 引言 本篇博客介绍了力扣经典150题中的第三十五题&#xff1a;螺旋矩阵。题目要求按照顺时针螺旋顺序遍历给定的…

华纳云:怎么防止租用服务器的数据丢失?

要防止租用服务器上的数据丢失&#xff0c;可以采取以下一些措施&#xff1a; 定期备份数据&#xff1a;建立定期备份数据的机制&#xff0c;将重要数据备份到安全的地方&#xff0c;例如云存储服务、外部硬盘或者另一个服务器上。备份频率可以根据数据的重要性和变动频率来确定…

[Kotlin]引导页

使用Kotlin Jetpack Compose创建一个左右滑动的引导页, 效果如图. 1.添加依赖项 androidx.compose.ui最新版本查询:https://maven.google.com/web/index.html com.google.accompanist:accompanist-pager最新版本查询:https://central.sonatype.com/ 确保在 build.gradle (M…

[Linux][多线程][二][线程互斥][互斥量][可重入VS线程安全][常见锁概念]

目录 1.线程互斥1.互斥相关背景概念2.多个线程并发的操作共享变量&#xff0c;会带来一些问题3.互斥量mutex 2.互斥量的接口1.初始化互斥量2.销毁互斥量3.加锁4.解锁5.使用 -- 改善上面代码 3.互斥量实现原理探究1.加锁是如何保证原子性的&#xff1f;2.如何保证锁是原子性的&a…

Unity的Animator Animation的使用攻略

Animator 动画控制器 Animation 动画 动画片段 .anin 一、创建Animator 创建动画控制器 模型添加Animator组件 把控制器和模型绑定 二、创建动画 进入动画界面 创建动画片段anin 动画窗口分析 制作动画 点击录制&#xff0c; 移动子对象&#xff0c;在视窗 通过移动线来编辑关…