模板中的 C++ 双链表

Posted

技术标签:

【中文标题】模板中的 C++ 双链表【英文标题】:C++ Doubly LinkedList in template 【发布时间】:2021-08-19 14:31:49 【问题描述】:

列表节点代码:

template <typename T>
struct ListNode 
public:
    T data;
    ListNode *prev, *next;
    ListNode() 
        prev = nullptr;
        next = nullptr;
    
    ListNode(T Data, ListNode *Prev, ListNode *Next) 
        data = Data;
        prev = Prev;
        next = Next;
    
;

双向链表代码:

#include <iostream>
#include <stdexcept>
using namespace std;

template <typename T>
class List 
protected:
        ListNode<T> *head, *tail;
public:
        List<T>() 
            head = NULL;
            tail = NULL;
        
        ~List<T>() 
            while (head != NULL) 
                pop_front();
            
        
        bool empty() const 
            if (head == NULL)
                return true;
            else
                return false;
        
        void push_front(T data) 
            if (head != NULL) 
                head = new ListNode<T>(data, NULL, head);
                head -> next -> prev = head;
            
            else 
                head = new ListNode<T>(data, NULL, NULL);
                tail = head; 
                   
        
        void push_back(T data) 
            if (tail != NULL) 
                tail = new ListNode<T>(data, tail, NULL);
                tail -> prev -> next = tail;
            
            else 
                tail = new ListNode<T>(data, NULL, NULL);   
                head = tail;
              
        
        void pop_front() 
            if (head != NULL) 
                ListNode<T> *temp = head;
                head = head -> next;
                delete temp;
            
            else
                throw out_of_range("This list is empty.");
        
        void pop_back() 
            if (tail != NULL) 
                ListNode<T> *temp = tail;
                tail = tail -> prev;
                delete temp;
            
            else
                throw out_of_range("This list is empty.");
        
        friend std::ostream& operator << (std::ostream& out, const List<T>& list) 
            out << list.head -> data;
            ListNode<T> *temp = list.head -> next;
            while (temp != NULL) 
                out <<  ", " << temp -> data;
                temp = temp -> next;
            
            return out; 
     
;

双向链表需要做push_front、push_back、pop_front、pop_back、pop_front、pop_back和bool empty。

outstream需要用“,”分隔数据

我发给在线评委了,但运行时出错。

我不知道这段代码有什么问题。

如何改正?

感谢大家的帮助。

【问题讨论】:

您是否使用调试器运行您的代码? 在创建一个新的头部或尾部后,您可以通过访问 ->next->prev 获得 UB 【参考方案1】:

您的问题出在pop_back() 函数中。

void pop_back() 
    if (tail != NULL) 
        ListNode<T> *temp = tail;
        tail = tail -> prev;
        delete temp;
    
    else
        throw out_of_range("This list is empty.");
    

您将尾部设置为新尾部,但您忘记将新的tail-&gt;next 更新为nullptr,因此它仍然指向old 尾部,您在delete temp; 行中释放了所有您需要做的就是在 ListNode&lt;T&gt; *temp = tail; 之后添加这一行tail-&gt;prev-&gt;next = nullptr;

所以它看起来像这样:

void pop_back() 
    if (tail != NULL) 
        ListNode<T> * temp = tail;
        tail->prev->next = nullptr;
        tail = tail->prev;
        delete temp;
    
    else
        throw out_of_range("This list is empty.");
    
also as a

旁注,如果您使用的是 c++ 11 及更高版本,您可以使用 auto 关键字,它将为您节省 ListNode&lt;T&gt; 而不是 auto* 您也可以保留 * 并继续使用 @987654334 @ 但我认为添加 * 更具可读性,因此很明显它是一个指针。

【讨论】:

@drescherjm 在哪里?在 OP 中还是在我的答案中?

以上是关于模板中的 C++ 双链表的主要内容,如果未能解决你的问题,请参考以下文章

c++学习笔记_c++实现双链表

c++,在哈希表中显示内容的方法。使用双链表

c++双链表构造函数运算符重载析构函数增删查改及逆置等

深度解析数组单链表和双链表

C++实现双向链表的所有操作,包括逆置双链表(三种方法)

有序的双链表的实现