将链表更改为双向链表

时间:2015-01-06 20:11:53

标签: c++ templates doubly-linked-list

您好,请您帮我将此链表更改为双向链表? 我非常感谢你的帮助:)。

#include <iostream>
using namespace std;

template <class T>
struct node
{
    T data;
    node<T> *next;
    node<T> *prev;
};

template <class T>
class Container
{

public:
    //constructs a new empty Kontener
    Container()
    {
        head = new node<T>;
        head->next = head;
        head->prev = head;
    };

//构造一个新的jp_list,它是现有列表的副本

 Container(const Container<T>& rt_side)
    {
        head = new node<T>;
        head->next = head;
        head->prev = head;

        node<T> *crt_ptr = rt_side.head->next;
        while(crt_ptr != rt_side.head)
        {
            push_back(crt_ptr->data);
            crt_ptr = crt_ptr->next;
        }
    };

    //adds a data node to the front of the list
    void push_front(T nw_data)
    {
        node<T> *temp = new node<T>;
        temp->data = nw_data;

        temp->next = head->next;
        head->next->prev = temp;

        temp->prev = head;
        head->next = temp;
    };

    //adds a data node to the end of the list
    void push_back(T nw_data)
    {
        node<T> *temp = new node<T>;
        temp->data = nw_data;

        head->prev->next = temp;
        temp->prev = head->prev;

        temp->next = head;
        head->prev = temp;
    };

    //removes the first node and returns the data
    T pop_front()
    {
        node<T> *temp = head->next;
        T temp_data = head->next->data;

        head->next = temp->next;
        temp->next->prev = head;

        delete temp;

        return temp_data;
    };

    //removes the last node and returns the data
    T pop_back()
    {
        node<T> *temp = head->prev;
        T temp_data = head->prev->data;

        head->prev = temp->prev;
        temp->prev->next = head;

        delete temp;

        return temp_data;
    };

    //resturns the size of the list
    int size()
    {
        int size = 0;
        node<T> *crt_ptr; //pointer to current node

        crt_ptr = head->next;
        while(crt_ptr != head)
        {
            size += 1;
            crt_ptr = crt_ptr->next; //advance to the next node then loop
        }

        return size;
    };

    //prints out all the data in the list
    void display_all()
    {
        node<T> *crt_ptr = head->next;

        for(int i = 0; crt_ptr != head; i++)
        {
            cout << "Node " << (i+1) << ": " << crt_ptr->data << endl;

            crt_ptr = crt_ptr->next;
        }
    };

    Container& operator= (const Container& rt_side)
    {
        if(this == &rt_side)
            return *this;
        node<T> *crt_ptr = head->next;

        //empty this list so the rt_side can be coppied in
        while(crt_ptr != head)
        {
            crt_ptr = crt_ptr->next;
            pop_front();
        }

        crt_ptr = rt_side.head->next;

        while(crt_ptr != rt_side.head)
        {
            push_back(crt_ptr->data);
            crt_ptr = crt_ptr->next;
        }

        return *this;
    };

    virtual ~Container()
    {
        int list_size = size();

        for(int i = 0; i < list_size; i++)
        {
            pop_front();
        }

        delete head;
    };

private:
    node<T> *head;

};

#endif

我只是一个初学者所以请帮助我:)。

1 个答案:

答案 0 :(得分:0)

尾部总是指向插入列表的最后一个项目。

但是,我不认为有一个尾指针使它必然是一个双向链表。单链表也可以有尾指针(但可能没用)。我相信你要求创建一个双端双链表。

您已经拥有了启用双链接的下一个和上一个指针。您所要做的就是,当您将某些内容推入列表时,您需要使尾指针指向正在添加的节点。类似地,在删除节点时,您需要尾部指针指向尾部之前删除最后一个节点。

*更新* 这是一些代码。我假设一个带有两端的双端双链表。

void push_front(T nw_data)
{
    node<T> *temp = new node<T>;
    temp->data = nw_data;

    if(head == nullptr)
    {
        head = temp;
        tail = temp;
    }
    else if(head == tail)
    {
        head->next = temp;
        temp->prev = head;
        tail = temp;
    }
    else
    {
        temp->next = head->next;
        head->next->prev = temp;

        temp->prev = head;
        head->next = temp;        
    }        
};

//adds a data node to the end of the list
void push_back(T nw_data)
{
    node<T> *temp = new node<T>;
    temp->data = nw_data;

    if(head == nullptr)
    {
        head = temp;
        tail = temp;
    }
    else if(head == tail)
    {
        head->next = temp;
        temp->prev = head;
        tail = temp;
    }
    else
    {
        temp->prev = tail;
        tail->next = temp;
        tail = temp;      
    }  
};

T pop_back()
{
    node<T> *temp = tail;
    T temp_data = tail->data;

    tail = tail->prev;
    tail->next = null;

    delete temp;

    return temp_data;
};

*更新* 复制构造函数 在你的拷贝构造函数中,如果push_back设置尾部,那么你需要做的就是按照你正在做的方式推送节点。 head-&gt; next = head and head-&gt; prev = head使链表循环。

Container(const Container<T>& rt_side)
{
    this->head = rt_side.head;

    node<T> * crt_ptr = rt_side.head->next;

    while (crt_ptr != null)
    {
        push_back(crt_ptr->data);

        crt_ptr = crt_ptr->next;
    }
};