C++序列式容器list的用法

本文主要介绍list的基本定义和基本使用,以及优缺点。

  1. 什么是序列式容器?(线性表-数组)
  2. list 相比于其它容器有什么优点?
  3. list的基本使用。


文章目录

  • C++序列式容器list的用法
  • 一、序列式容器和list是什么?
  • 二、使用步骤
  • 1.测试一(添加元素和排序):
  • 2.测试二(删除操作)




一、序列式容器和list是什么?

1. 序列式容器:
所谓序列容器,即以线性排列(类似普通数组的存储方式)来存储某一指定类型(例如 int、double 等)的数据,也可以说是数据结构中的线性表。

该类容器并不会自动对存储的元素按照值的大小进行排序。

2. list 的基本定义:

  • list(链表容器):是一个长度可变的、由 T 类型元素组成的序列
  • 它以双向链表的形式组织元素,在这个序列的任何地方都可以高效地增加或删除元素(时间复杂度都为常数阶 O(1)),不需要前移或者后移

这里是因为插入一个数据,这里做一个简单的例子:a b d,其中这三个节点都有自己的头指针和尾指针。
这里想在节点:b和节点:d之间插入节点:c
只需要把b的尾指针指向c、d的头指针指向c、c的头指针指向b、c的尾指针指向d。

访问容器中任意元素的速度要比前三种容器慢,时间复杂度为O(n)

这是因为 list<T>必须从第一个元素或最后一个元素开始访问,需要沿着链表移动,直到到达想要的元素。

3. list相比array、vector 和 dequelist容器的优点和缺点:
优点:

  • 可以在序列已知的任何位置快速插入或删除元素(时间复杂度为O(1))。
  • list 容器中移动元素,也比其它容器的效率高。

缺点:

  • 不能够直接通过位置直接访问元素(通过下标去访问元素)。

这里的优缺点可以通过上面list的基本定义去理解。

二、使用步骤

list基本函数汇总如下表格:

begin()

返回指向容器中第一个元素的双向迭代器。

end()

返回指向容器中第一个元素的双向迭代器。

rbegin()

返回指向最后一个元素的反向双向迭代器。

rend()

返回指向第一个元素所在位置前一个位置的反向双向迭代器。

cbegin()

和 begin() 功能相同,只不过在其基础上,增加了 const 属性,不能用于修改元素。

cend()

和 end() 功能相同,只不过在其基础上,增加了 const 属性,不能用于修改元素。

crbegin()

和 rbegin() 功能相同,只不过在其基础上,增加了 const 属性,不能用于修改元素。

crend()

和 rend() 功能相同,只不过在其基础上,增加了 const 属性,不能用于修改元素。

empty()

判断容器中是否有元素,若无元素,则返回 true;反之,返回 false。

size()

返回当前容器实际包含的元素个数。

max_size()

返回容器所能包含元素个数的最大值。这通常是一个很大的值,一般是 232- 1,所以我们很少会用到这个函数。

front()

返回第一个元素的引用。

back()

返回最后一个元素的引用。

assign()

用新元素替换容器中原有内容。

emplace_front()

在容器头部生成一个元素。该函数和 push_front() 的功能相同,但效率更高。

push_front()

在容器头部插入一个元素。

pop_front()

删除容器头部的一个元素。

emplace_back()

在容器尾部直接生成一个元素。该函数和 push_back() 的功能相同,但效率更高。

push_back()

在容器尾部插入一个元素。

pop_back()

删除容器尾部的一个元素。

emplace()

在容器中的指定位置插入元素。该函数和 insert() 功能相同,但效率更高。

insert()

在容器中的指定位置插入元素。

erase()

删除容器中一个或某区域内的元素。

swap()

交换两个容器中的元素,必须保证这两个容器中存储的元素类型是相同的。

resize()

调整容器的大小。

clear()

删除容器存储的所有元素。

splice()

将一个 list 容器中的元素插入到另一个容器的指定位置。

remove(val)

删除容器中所有等于 val 的元素。

remove_if()

删除容器中满足条件的元素。

unique()

删除容器中相邻的重复元素,只保留一个。

merge()

合并两个事先已排好序的 list 容器,并且合并之后的 list 容器依然是有序的。

sort()

通过更改容器中元素的位置,将它们进行排序。

reverse()

反转容器中元素的顺序。

1.测试一(添加元素和排序):

代码如下(示例):

#include <list>
#include <iostream>
int main()
{
    //创建空的 list 容器
    std::list<double> values;
    //向容器中添加元素
    values.push_back(3.1);
    values.push_back(2.2);
    values.push_back(2.9);
    cout << "values size:" << values.size() << endl;
    //对容器中的元素进行排序
    values.sort();
    //使用迭代器输出list容器中的元素
    for (std::list<double>::iterator it = values.begin(); it != values.end(); ++it)
    {
        std::cout << *it << " ";
    }
  
    return 0;
}

运行截图:

不使用容器化技术_迭代器

2.测试二(删除操作)

代码如下(示例):

#include <list>
#include <iostream>
using namespace std;
int main()
{
	//声明对象
	list<int> elems;
	//向链表的最后放入元素
	elems.push_back(8);
	elems.push_back(5);
	//向链表的前端放入元素
	elems.push_front(2);
	// 2  8  5
	//使用foreach循环,遍历容器,遍历的是list 
	for (int a : elems)
	{
		cout << "元素:" << a << endl;
		//输出 2 8 5
	}
	cout << "删除首位元素后" << endl;
	//删除元素
	elems.erase(elems.begin());
	//定义了一个迭代器
	list<int>::iterator iter;
	//  8 5
	//使用迭代器循环,遍历容器,遍历的是list
	for (iter = elems.begin(); iter != elems.end(); iter++)
	{
		cout << "元素:" << *iter << endl;
		// 8 5 
	}

	if (!elems.empty())
	{
		cout << "elems 不为空" << endl;
	}

	cout << "elems 的长度为:" << elems.size() << endl;
	
    return 0;
    
}

运行截图:

不使用容器化技术_list_02