关于链表的一些重要操作(Important operations on a Linked List)

上篇博文中讨论了链表的一些基本操作:

然而,为创建一个多功能的链表,在深度学习之前我们还需要了解更多的链表操作。

  • 在表头插入元素。
  • 在表中插入元素。
    • 在确定的位置插入。
    • 在某个元素的后面插入。
  • 从链表中删除一个元素。
  • 删除整个链表。

在链表头部插入元素

为了在链表头部插入元素,我们要完成一项小任务:创建一个临时节点,把数据存入这个临时节点,将这个节点指向链表的头节点。

/*
Defining a function to add an element at the beginning of the Linked List
*/
struct node * addAtBeg(struct node * head, int number)
{
    //making a temporary node
    struct node * temp = (struct node*)malloc(sizeof(struct node));

    //assigning the necessary values
    temp -> data = number;
    temp -> next = head;

    //we make the new node as the head node and return
    return temp;
}

在链表的特定位置插入数据

依然创建临时节点,把要插入的数据存入这个节点。将临时节点指向指定位置(假定指定位置在两个节点中间)的下个节点,把指定位置上个节点指向临时节点。

/*Defining a function to add at a particular position in a Linked List*/
struct node * addAtPos(struct node *head, int number, int pos)
{
    //this is our initial position
    int initial_pos = 0;

    //This is a very important statement in all Linked List traversals
    //Always create some temporary variable to traverse the list.
    //This is done so that we do not loose the starting point of the
    //Linked List, that is the HEAD
    struct node * mover = head;

    while(initial_pos != pos)
    {
        //we need to traverse the Linked List, until
        //we reached the userdefined position
        mover = mover -> next;

        //incrementing initial position
        initial_pos++;
    }

    //Now mover points to the user defined position

    //Create a temporary node
    struct node * temp = (struct node*)malloc(sizeof(struct node));
    temp -> data = number;

    //Inserting the node.
    temp -> next = mover -> next;
    mover -> next = temp;

    return head;
}

在指定节点后插入数据

整个过程其实和上面的一样,唯一的区别是我们需要遍历整个链表找到指定节点,然后执行过程大同小异。

/*
Defining a function to insert after a specified node
*/
struct node * addAfterNode(struct node * head, int number, int after_num)
{
    //creating a temporary node to iterate
    struct node * mover = head;

    while(mover -> data != after_num)
    {
        // We need to iterate until we reach the desired node
        mover = mover -> next;
    }

    //Now mover points at the node that we want to insert

    struct node *temp = (struct node*)malloc(sizeof(struct node));
    temp -> data = number;
    temp -> next = mover -> next;
    mover -> next = temp;

    return head;
}

删除节点

删除节点,我们需要遍历链表找到要删除的节点。删除节点不需要什么高级的操作,只要将被删除节点的前个节点的next指向被删除节点的下个节点就完成了。

/*
Defining a function to delete a node in the Linked List
*/
struct node * deleteANode(struct node * head, int node_data)
{
    //In this function we will try to delete a node that
    //has the particular node data given by the user

    struct node * mover = head;

    //Creating a variable to store the previous node
    struct node * prev;

    while(mover -> data != node_data)
    {
        prev = mover;
        mover = mover -> next;
    }

    //Now mover point to the node that we need to delete
    //prev points to the node just before mover.

    //Deleting the node mover
    prev -> next = mover -> next;

    return head;
}

删除整个链表

简单清空HEAD就能删除整个链表,但数据仍然在内存中,只是丢失对它的连接。要彻底删除我们可以用free()函数。

/*
Defining a function to delete the entire List
*/
struct node * deleteList(struct node * head)
{
    struct node * temp;

    while(head != NULL)
    {
        temp = head;
        head = head -> next;
        free(temp);
    }

    return NULL;
}

完整代码如下:

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

//creating the basic structure of a node of a Linked List
struct node
{
    int data;
    struct node * next;
};

/*
Code obtained from

http://www.studyalgorithms.com
*/
/* Defining a function to create a new list.
The return type of the function is struct node, because we will return the head node
The parameters will be the node, passed from the main function.
The second parameter will be the data element.
*/
struct node * createList(struct node *head,int number)
{
    //creating a temporary node for our initialization purpose

    //the below line allocates a space in memory that can hold the data in a node.
    struct node *temp = (struct node *)malloc(sizeof(struct node));

    //assigning the number to data
    temp -> data = number;

    //assigning the next of this node to NULL, as a new list is formed.
    temp -> next = NULL;

    //now since we have passed head as the parameter, we need to return it.
    head = temp;
    return head;
}

/*
Defining a case when we need to element in the Linked List.
Here 2 cases can arise:-
    -The Linked List can be empty, then we need to create a new list
    -The Linked List exists, we need to add the element
*/
struct node * addElement(struct node *head, int number)
{
    if(head == NULL)
        head = createList(head, number);   // we can directly call the above function
    else
    {
        // now this is a case when we need to add an element to an existing list.

        //Creating a new node and assigning values
        struct node * temp = (struct node*)malloc(sizeof(struct node));
        temp -> data = number;
        temp -> next = NULL;

        //Now we have created the node but, we need to insert it at the right place.
        //A Linked List terminates when we encounter a NULL
        //Feel free to copy but please acknowledge studyalgorithms.com
        //Let us traverse the List using another temporary variable.
        //We will point it to the start
        struct node * temp2 = head;

        //The limiting condition of the while loop "until temp2‘s NEXT is not equal to NULL
        //This will happen only in case of the last node of the list.
        while(temp2 -> next != NULL)
        {
            // We need to go to the next node
            temp2 = temp2 -> next;
        }

        //Now temp2 points at the last node of the list.
        //We can add the node at this position now.

        temp2 -> next = temp;  // the number is added to the end of the List.
    }

    return head; // because we only need the HEAD pointer for a Linked List.
}

/*
A function to print the Linked List.
The return type of this function will be void, as we do not need to return anything.
We just need the HEAD as the parameter, to traverse the Linked List.
*/
void printList(struct node * head)
{
    printf("\nThe list is as:- \n");
    // The terminating point of a Linked List is defined when we encounter a NULL
    while(head != NULL)
    {
        printf("%d ",head->data);

        //now we need to move to the next element
        head = head->next;
        //Feel free to copy but please acknowledge studyalgorithms.com
    }
    printf("\n");
}

/*
Defining a function to add an element at the beginning of the Linked List
*/
struct node * addAtBeg(struct node * head, int number)
{
    //making a temporary node
    struct node * temp = (struct node*)malloc(sizeof(struct node));

    //assigning the necessary values
    temp -> data = number;
    temp -> next = head;

    //we make the new node as the head node and return
    return temp;
}

/*Defining a function to add at a particular position in a Linked List*/
struct node * addAtPos(struct node *head, int number, int pos)
{
    if(head == NULL)
    {
        printf("\nList is EMPTY");
        return NULL;
    }
    //this is our initial position
    int initial_pos = 0;

    //This is a very important statement in all Linked List traversals
    //Always create some temporary variable to traverse the list.
    //This is done so that we do not loose the starting point of the
    //Linked List, that is the HEAD
    struct node * mover = head;

    while(initial_pos != pos)
    {
        //we need to traverse the Linked List, until
        //we reached the userdefined position
        mover = mover -> next;

        //incrementing initial position
        initial_pos++;
        //Feel free to copy but please acknowledge studyalgorithms.com
    }

    //Now mover points to the user defined position

    //Create a temporary node
    struct node * temp = (struct node*)malloc(sizeof(struct node));
    temp -> data = number;

    //Inserting the node.
    temp -> next = mover -> next;
    mover -> next = temp;

    return head;
}

/*
Defining a function to insert after a specified node
*/
struct node * addAfterNode(struct node * head, int number, int after_num)
{
    if(head == NULL)
    {
        printf("\nList is EMPTY");
        return NULL;
    }

    //creating a temporary node to iterate
    struct node * mover = head;

    while(mover -> data != after_num)
    {
        // We need to iterate until we reach the desired node
        mover = mover -> next;
    }

    //Now mover points at the node that we want to insert

    struct node *temp = (struct node*)malloc(sizeof(struct node));
    temp -> data = number;
    temp -> next = mover -> next;
    //Feel free to copy but please acknowledge studyalgorithms.com
    mover -> next = temp;

    return head;
}

/*
Defining a function to delete a node in the Linked List
*/
struct node * deleteANode(struct node * head, int node_data)
{
    if(head == NULL)
    {
        printf("\nList is EMPTY");
        return NULL;
    }

    //In this function we will try to delete a node that
    //has the particular node data given by the user

    struct node * mover = head;

    //Creating a variable to store the previous node
    struct node * prev;

    while(mover -> data != node_data)
    {
        prev = mover;
        mover = mover -> next;
    }

    //Now mover point to the node that we need to delete
    //prev points to the node just before mover.

    //Deleting the node mover
    prev -> next = mover -> next;

    return head;
}

/*
Defining a function to delete the entire List
*/
struct node * deleteList(struct node * head)
{
    if(head == NULL)
    {
        printf("\nList is EMPTY");
        return NULL;
    }

    struct node * temp;

    while(head != NULL)
    {
        temp = head;
        head = head -> next;
        free(temp);
    }

    return NULL;
}

//Defining the main function to implement all the above defined functions
int main(void)
{
    int choice = 10;
    int flag = 0;
    int num;
    int pos;

    struct node *listHead = NULL;

    while(flag != 1)
    {
        printf("\nWhat do you want to do?\n1.>Create a List\n2.>Add an element at the end\n3.>Add an element at the beginning\n4.>Add an element at a position\n5.>Add an element after a certain element\n6.>Delete at node.\n7.>Print the List\n8.>Delet the List\n9.>Exit.\n\nEnter choice:- ");
        scanf("%d",&choice);

        switch(choice)
        {
            case 1:
            printf("Enter a number:- ");
            scanf("%d",&num);
            listHead = createList(listHead, num);
            //Feel free to copy but please acknowledge studyalgorithms.com
            printList(listHead);
            break;

            case 2:
            printf("Enter a number:- ");
            scanf("%d",&num);
            listHead = addElement(listHead, num);
            printList(listHead);
            break;

            case 3:
            printf("Enter a number:- ");
            scanf("%d",&num);
            listHead = addAtBeg(listHead, num);
            printList(listHead);
            break;

            case 4:
            printf("Enter a number:- ");
            scanf("%d",&num);
            printf("Enter a position:- ");
            scanf("%d",&pos);
            listHead = addAtPos(listHead, num, pos);
            printList(listHead);
            break;

            case 5:
            printf("Enter a number:- ");
            scanf("%d",&num);
            printf("Enter a node:- ");
            scanf("%d",&pos);
            listHead = addAfterNode(listHead, num, pos);
            printList(listHead);
            break;

            case 6:
            printf("Enter a node to delete:- ");
            scanf("%d",&num);
            listHead = deleteANode(listHead, num);
            printList(listHead);
            break;

            case 7:
            printList(listHead);
            break;

            case 8:
            listHead = deleteList(listHead);
            break;

            case 9:
            flag = 1;
            break;

            default:
            printf("Invalid choice\n");
            //Feel free to copy but please acknowledge studyalgorithms.com
            break;
        }
    }

    return 0;
}

时间: 2024-10-13 00:44:48

关于链表的一些重要操作(Important operations on a Linked List)的相关文章

链表的特有算法操作

10.42 使用list的算法实现排序和删除重复元素. #include<algorithm> #include<list> #include<iostream> #include<string> using namespace std; void elimDup(list<string> &words) { words.sort(); words.unique(); } bool isShorter(const string &

关于链表的一些简单操作

终于上黄金了.. 然后就是一波2连败... 最近 完全不想做题啊  一做题 就想碎觉啊 郁闷死了 根据书本 写了点关于单向链表的简单操作 可能还存在点小bug---先放它一马吧 以后可能再进行补充关于它的操作 毕竟还有好多 先慢慢找回敲键盘打代码的感觉 厌 1 /* 2 线性表之单向链表的一些常见操作 3 */ 4 #include <iostream> 5 using namespace std; 6 7 typedef int ElemType; 8 typedef struct LNod

静态链表的实现与操作(C语言实现)

我们知道要实现单链表,必须要有指针,那么像Java这样没有指针的的语言就略显蛋疼了. 没关系,我们有静态链表,其本质就是用采用数组的方式实现单链表的功能. 头文件: #ifndef _StaticLinkList_H_ #define _StaticLinkList_H_ typedef void StaticLinkList; typedef void StaticLinkListNode; StaticLinkList * StaticLinkList_Create(int capacity

链表的基本操作(Basic Operations on a Linked List)

链表可以进行如下操作: 创建新链表 增加新元素 遍历链表 打印链表 下面定义了对应以上操作的基本函数. 创建新链表 新链表创建之后里面并没有任何元素,我们要为数据在内存中分配节点,再将节点插入链表.由于这个链表只有一个节点,它所指向的下一个节点为NULL. /* Defining a function to create a new list. The return type of the function is struct node, because we will return the h

链表的无锁操作 (JAVA)

看了下网上关于链表的无锁操作,写的不清楚,遂自己整理一部分,主要使用concurrent并发包的CAS操作. 1. 链表尾部插入 待插入的节点为:cur 尾节点:pred 基本插入方法: do{ pred = find_tail(); //重新找尾节点 }(! pred.next.compareAndSet(NULL, cur)) //pred.next 是否为NULL,是则将其指向cur,不是则有新的节点插入 这种插入方法是不带标记的,如果不涉及链表删除这个方法是可行的. 但是如果有删除操作,

链表及其各种函数操作的实现方法

代码中主要实现了下面四个操作: 下面几种操作都是线性操作,算法复杂度都是O(n): 链表插入默认是按关键字大小插入链表的,所以最后得到的结果是从大到小排好序的,分三种情况(1)链表为空(2)插入的点最小,插在链表最前面:(3)插入链表中间;(4)插入链表结尾. 链表删除是在链表中找到要删除的关键字,然后删除该节点,如果有两个以上,只删一个.如果没有就返回.删除操作必须释放删除结点所申请的内存: 查找最大理论上就是最后一个,查找最小理论上就是第一个结点.但是我为了通用性写成了遍历整个链表查找最大和

单链表反转的图示操作

有一个线性表$(a_1,a_2, \cdots, a_n)$, 采用带头结点的单链表$L$存储,设计一个算法将其就地逆置.所谓“就地”指辅助空间为$O(1)$. 解答:用$p$指针扫描原单链表,先将头结点$L$的$next$域置为$NULL$而变成一个空链表,然后,将$*p$结点采用头插法插入到$L$中.算法如下: 1 void Reverse(LinkList *&L){ 2 LinkList *p=L->next,*q; 3 L->next=NULL; 4 while (p!=NU

单链表 - 插入和删除操作

下图展示了单链表的基本结构: head指针是链表的头指针,指向第一个节点,每个节点的next指针域指向下一个节点,最后一个节点的next指针域为NULL,在图中用0表示. 下面先来看程序(栈的链式存储实现,另外一个实现点这里)和对应的输出(注意输出前进行了链表反转(见<单链表反转>,否则程序后面的while循环输出的顺序是250,200,100),接着来分析程序: C++ Code 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22

C++单链表的创建与操作

链表是一种动态数据结构,他的特点是用一组任意的存储单元(可以是连续的,也可以是不连续的)存放数据元素.链表中每一个元素成为“结点”,每一个结点都是由数据域和指针域组成的,每个结点中的指针域指向下一个结点.Head是“头指针”,表示链表的开始,用来指向第一个结点,而最后一个指针的指针域为NULL(空地址),表示链表的结束.可以看出链表结构必须利用指针才能实现,即一个结点中必须包含一个指针变量,用来存放下一个结点的地址.结点中只有一个next指针的链表称为单链表,这是最简单的链表结构. 首先定义一个