数据结构之单链表(c++)

201 阅读3分钟

1.类内定义

类中定义了链表的初始化、插入、删除、获取元素等方法。

class List{
public:
    List(){    //初始化链表
        this->size=0;
        this->L=new LinkList;
        L->next=NULL;
    }
    void insertFront(int e);    //头插法
    void insertLast(int e);    //尾插法
    int getSize();    //获取单链表长度
    void print();    //遍历输出
    bool deleListElement(int i);    //删除第i个元素
    int getListElement(int i);    //获取第i个元素
    bool insert(int i,int e);   //在第i个元素前插入元素
    struct LinkList{
        int data;
        LinkList* next;
    };
private:
    int size;    //表示单链表的长度
    LinkList *L;    //头指针
 };

结构体定义链表,每个节点包含一个int类型的data和一个指向下一个节点的指针next。

构造函数为私有成员赋值,size赋值为0,创建头节点,头指针L指向头节点,L的next指向空。

2.类外实现

(1)头插法

d37a7c9c5e5ccf9587cbf487fe4a2e5.jpg

void List::insertFront(int e){
    LinkList *p=new LinkList;    //创建新的节点
    p->data=e;
    p->next=L->next;
    L->next=p;
    this->size++;
}

传递的e为p节点的data值,将L节点的next值赋给p节点的next,L节点的next指针域指向p。每增加一个节点,单链表的长度size+1。

(2)尾插法

2b0da1f93660323c187a274fc58163a.jpg

void List::insertLast(int e){
    LinkList *p=new LinkList;    //创建新的节点
    p->data=e;
    LinkList *r;
    r=L;
    while(r->next){
        r=r->next;
    }
    r->next=p;
    p->next=NULL;
    this->size++;
}

传递的e为p节点的data值,r为尾指针,r节点的next指针域指向p,新增的p节点的next指针域指向空。每增加一个节点,单链表的长度size+1。

(3)获取单链表长度

int List::getSize(){
    return this->size;
}  

私有成员size记录单链表的长度,且在链表初始化的时候赋值为0,每增加一个节点size+1。

(4)遍历输出

void List::print(){
    LinkList *p;
    p=L->next;
    while(p->next){
        cout<<p->data<<" ";
        p=p->next;
    }
    cout<<p->data<<" ";
}

p指向首节点,循环遍历输出p的data值。由于循环的跳出条件为p->next,当p指向最后一个节点时无法进入循环,故需再输出最后一个节点的data值。

(5)删除第i个元素

171b42936861d12e74bf29dd1cc62f3.jpg

bool List::deleListElement(int i){
    if(this->size<i||i<0){
        return false;
    }
    LinkList *r;
    r=L;
    int j=0;
    while(r->next&&j<i-1){
        r=r->next;
        j++;
    }
    LinkList *p=r->next;
    r->next=p->next;
    delete(p);
    return true;		
}

首先,判断插入位置i的合法性,不合法直接返回false。合法则创建一个r指针指向L,j计数,通过while循环使r指向i-1个节点,再创建一个p节点指向r->next,即指向第i个节点。将r节点的next指针域指向p->next节点,即指向第i+1个节点。最后释放p节点。

(6)获取第i个元素

int List::getListElement(int i){
    if(this->size<i||i<0){
        return -1;
    }	  		 
    LinkList* p;
    p=L;
    int j=0;
    while(p->next&&j<i){
        p=p->next;
        j++;
    }
    return p->data;
}

首先,判断插入位置i的合法性,不合法直接返回-1(假设链表里面的数据都是大于-1的,也可以根据自己的需求设计返回值)。合法则创建一个p指针指向L,j计数,通过while循环使p指向第i个节点,返回其data值。

(7)在第i个元素前插入元素

608fe8efb0563c7382cd1f29e586a3c.jpg

bool List::insert(int i,int e){
    if(this->size<i||i<0){
        return false;
    }
    LinkList* r;
    r=L;
    int j=0;
    while(r->next&&j<i-1){
        r=r->next;
        j++;
    }
    LinkList* p=new LinkList;
    p->data=e;
    p->next=r->next;
    r->next=p;
    this->size++;
    return true;		  		  
}

使用while循环使r指针指向第i-1个元素,创建一个新节点p,将e赋值给p->data,p节点的指针域next指向r->next,再将r节点的指针域next指向p节点,单链表的长度size+1。