list基本使用

本文详细介绍了C++标准库中的list容器,包括其构造方式、迭代器操作、容量检查、访问和修改元素的方法,以及注意事项,如迭代器失效问题。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >


list容器底层是带头双向链表结构,可以在常数范围内在任意位置进行输入和删除,但不支持任意位置的随机访问(如不支持[ ]下标访问),下面介绍list容器的基本使用接口。

template < class T, class Alloc = allocator > class list;

在这里插入图片描述

构造

1.无参构造

 list()

2.使用n个元素val进行构造

list(size_type n,const value_type& value = value_type());

3,拷贝构造

list(const list& x);

4.使用迭代器区间进行构造

list(InputIterator first, InputIterator last);

迭代器

1.正向迭代器

	  iterator begin();
const_iterator begin() const;
       
      iterator end();
const_iterator end() const;

2.反向迭代器

	  reverse_iterator rbegin();
const_reverse_iterator rbegin() const;

      reverse_iterator rend();
const_reverse_iterator rend() const;

容量

1.判断链表是否为空

bool empty() const;

2.获取链表中有效节点个数

size_type size() const;

3.修改容量大小

void resize (size_type n, value_type val = value_type());

访问

1.获取链表第一个节点的值的引用

      reference front();
const_reference front() const;

2.获取链表最后一个节点的值的引用

      reference back();
const_reference back() const;

修改

1.元素首插

void push_front (const value_type& val);

2.元素尾插

void push_back (const value_type& val);

3.在position位置插入值为val的元素

iterator insert (iterator position, const value_type& val);
void insert (iterator position, size_type n, const value_type& val);

template <class InputIterator>
void insert (iterator position, InputIterator first, InputIterator last);

//Notice that the range includes all the elements between first and last, including the element pointed by first but not the one pointed by last.

5.元素首删

void pop_front();

6.元素尾删

void pop_back();

7.删除position位置的元素

iterator erase (iterator position);
iterator erase (iterator first, iterator last);

//the range includes all the elements between first and last, including the element pointed by first but not the one pointed by last.

8.清空链表有效元素

void clear();

9.交换两个链表的所有元素

void swap (list& x);

需要注意的是,list在进行插入操作时,不需要移动数据,因此进行元素插入不会导致迭代器失效,但在进行元素删除时,指向删除元素的迭代器会失效,其他的并没有影响。

list具体使用可以查看相关文档:list

模拟实现

#include <assert.h>
#include <iostream>

using namespace std;

namespace roman {
// List的节点类
template <class T> struct ListNode {
    ListNode(const T& val = T()) : 
        _val(val), 
        _next(nullptr), 
        _pre(nullptr) 
    {}
    ListNode<T>* _pre;
    ListNode<T>* _next;
    T _val;
};

// List的迭代器类
template <class T, class Ref, class Ptr> class ListIterator {
    template <class T> friend class list;
    typedef ListNode<T>* PNode;
    typedef ListIterator<T, Ref, Ptr> Self;

public:
    ListIterator(PNode pNode = nullptr) : _pNode(pNode) {}

    Ref operator*() { return _pNode->_val; }
    Ptr operator->() { return &(_pNode->_val); }

    Self& operator++() {
        _pNode = _pNode->_next;
        return *this;
    }

    Self operator++(int) {
        Self tmp = *this;
        _pNode = _pNode->_next;
        return tmp;
    }

    Self& operator--() {
        _pNode = _pNode->_pre;
        return *this;
    }

    Self& operator--(int) {
        Self tmp = *this;
        _pNode = _pNode->_pre;
        return tmp;
    }

    bool operator!=(const Self& l) { return _pNode != l._pNode; }
    bool operator==(const Self& l) { return _pNode == l._pNode; }

private:
    PNode _pNode;
};

// list类
template <class T> 
class list {
    typedef ListNode<T> Node;
    typedef Node* pNode;

public:
    typedef ListIterator<T, T&, T*> iterator;
    typedef ListIterator<T, const T&, const T&> const_iterator;

public:
    template <class T1>
    friend ostream& operator<<(ostream& out, const list<T1>& l);
    ///////////////////////////////////////////////////////////////
    // List的构造
    list() : _phead(new Node) {
        if (nullptr == _phead) {
            perror("new");
            return;
        }
        _phead->_next = _phead;
        _phead->_pre = _phead;
    }

    list(int n, const T& value = T()) : _phead(new Node) {
        if (nullptr == _phead) {
            perror("new");
            return;
        }
        _phead->_next = _phead;
        _phead->_pre = _phead;
        assert(n >= 0);
        pNode tail = _phead->_pre;
        while (n--) {
            pNode node = new Node(value);
            tail->_next = node;
            node->_pre = tail;
            node->_next = _phead;
            _phead->_pre = node;
            tail = node;
        }
    }

    template <class Iterator>
    list(Iterator first, Iterator last) : _phead(new Node) {
        if (nullptr == _phead) {
            perror("new");
            return;
        }
        _phead->_next = _phead;
        _phead->_pre = _phead;
        pNode tail = _phead->_pre;
        while (first != last) {
            pNode node = new Node(first->_val);
            tail->_next = node;
            node->_pre = tail;
            node->_next = _phead;
            _phead->_pre = node;
            tail = node;
            ++first;
        }
    }

    list(const list<T>& l) : _phead(new Node) {
        if (nullptr == _phead) {
            perror("new");
            return;
        }
        _phead->_next = _phead;
        _phead->_pre = _phead;
        pNode tail = _phead->_pre;
        pNode copy_node = (l._phead)->_next;
        while (copy_node != l._phead) {
            pNode node = new Node(copy_node->_val);
            tail->_next = node;
            node->_pre = tail;
            node->_next = _phead;
            _phead->_pre = node;
            tail = node;
            copy_node = copy_node->_next;
        }
    }

    list<T>& operator=(const list<T> l) {
        std::swap(_phead->_next, (l._phead->_next));

        return *this;
    }

    ~list() {
        pNode cur = _phead->_pre;
        while (cur != _phead) {
            cur = cur->_pre;
            delete cur->_next;
        }
        delete _phead;
        _phead = nullptr;
    }

    ///////////////////////////////////////////////////////////////
    // List Iterator
    iterator begin() { return iterator(_phead->_next); }
    iterator end() { return iterator(_phead); }
    const_iterator begin() const { return const_iterator(_phead->_next); }
    const_iterator end() const { return const_iterator(_phead); }

    ///////////////////////////////////////////////////////////////
    // List Capacity
    size_t size() const {
        int length = 0;
        pNode cur = _phead->_next;
        while (cur != _phead) {
            ++length;
            cur = cur->_next;
        }

        return length;
    }

    bool empty() const { return _phead == _phead->_next; }

    ////////////////////////////////////////////////////////////
    // List Access
    T& front() { return _phead->_next->_val; }
    const T& front() const { return _phead->_next->_val; }
    T& back() { return _phead->_pre->_val; }
    const T& back() const { return _phead->_pre->_val; }

    ////////////////////////////////////////////////////////////
    // List Modify
    void push_back(const T& val) { insert(end(), val); }
    void pop_back() { erase(--end()); }
    void push_front(const T& val) { insert(begin(), val); }
    void pop_front() { erase(begin()); }

    // 在pos位置前插入值为val的节点
    iterator insert(iterator pos, const T& val) {
        pNode node = new Node(val);
        (pos._pNode)->_pre->_next = node;
        node->_pre = (pos._pNode->_pre);
        node->_next = pos._pNode;
        (pos._pNode)->_pre = node;

        return iterator(node);
    }

    // 删除pos位置的节点,返回该节点的下一个位置
    iterator erase(iterator pos) {
        assert((pos._pNode) != _phead);
        (pos._pNode)->_pre->_next = (pos._pNode)->_next;
        (pos._pNode)->_next->_pre = pos._pNode->_pre;
        pNode tmp = (pos._pNode)->_next;
        delete pos._pNode;

        return iterator(tmp);
    }

    void clear() {
        pNode cur = _phead->_next;
        pNode next = cur->_next;
        while (cur != _phead) {
            delete cur;
            cur = next;
            next = next->_next;
        }
        _phead->_next = _phead;
        _phead->_pre = _phead;
    }

    void swap(list<T>& l) {
        pNode head = _phead->_next;
        pNode tail = _phead->_pre;
        _phead->_next->_pre = l._phead;
        _phead->_pre->_next = l._phead;
        (l._phead)->_next->_pre = _phead;
        (l._phead)->_pre->_next = _phead;
        _phead->_next = (l._phead)->_next;
        _phead->_pre = (l._phead)->_pre;
        (l._phead)->_next = head;
        (l._phead)->_pre = tail;
    }

private:
    pNode _phead;
};

template <class T1>
ostream& operator<<(ostream& out, const roman::list<T1>& l) {
    roman::ListNode<T1>* tail = (l._phead)->_next;
    while (tail != l._phead) {
        out << (tail->_val) << ' ';
        tail = tail->_next;
    }
    return out;
}
}; // namespace roman
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值