对于STL库中的容器来说,添加元素是一个容器最基本的要求。今天我们就来沉浸式学习为list容器添加元素。在那节《初识STL库中的list容器》(进入该页,ctrl+f5查找"插入"就能获取我们需要的函数)我们以表格的形式展示了list容器内的所有成员函数,我们可以两页并用,边查看边使用。

头插尾插(push_front()、push_back()不必多说;emplace_front()、emplace_back()也是头插尾插,但是是直接构造,为前者的“高效版”;当然,如果说按位置插入,参数有位置迭代器的话:insert()可插入单个或多个元素,emplace()只能插入单个元素;由于list的独特结构(指针链接数据),使其能够使用splice()进行链表之间的“拼接”,实现“移花接木”的效果。

我将展示所有需要的函数:

函数参数与功能简介
push_front参数: const value_type& val
功能: 在链表头部插入一个元素的副本
emplace_front参数: Args&&... args
功能: 在链表头部直接构造一个元素,无需创建临时对象,通常比 push_front 更高效。
push_back参数: const value_type& val
功能: 在链表尾部插入一个元素的副本
emplace_back参数: Args&&... args
功能: 在链表尾部直接构造一个元素,无需创建临时对象,通常比 push_back 更高效。
insert参数(单元素): iterator position, const value_type& val
功能: 在指定迭代器 position 之前插入一个元素的副本。

参数(多个元素): iterator position, size_type n, const value_type& val
功能: 在 position 之前插入 n 个 val 的副本。

参数(迭代器范围): iterator position, InputIterator first, InputIterator last
功能: 在 position 之前插入来自范围 [first, last) 的元素副本。
emplace参数: iterator position, Args&&... args
功能: 在指定迭代器 position 之前直接构造一个单个元素。这是 insert 单元素插入的高效版本。
splice参数(整个链表): iterator position, list& l
功能: 将链表 l 的全部元素移动到当前链表的 position 之前。操作后 l 为空。

参数(单个元素): iterator position, list& l, iterator i
功能: 将链表 l 中由迭代器 i 指向的单个元素移动到当前链表的 position 之前。

参数(元素范围): iterator position, list& l, iterator first, iterator last
功能: 将链表 l 中 [first, last) 范围内的元素移动到当前链表的 position 之前。

函数理解起来有点抽象,所以我们以代码为主,代码使用过哪些成员函数,我们再回过头来查看表格加深印象。下面我将通过代码的方式向您展示如何为list插入元素:

#include<bits/stdc++.h>
#include<list>
/* 如何为list容器添加元素 */
using namespace std;
/*通过push_back()、push_front()、emplace_back()、emplace_front()为list添加单个元素*/ 
void test1()
{
/*只能添加单个元素*/
list<int> l{1,2,3,4,5};//初始化链表 
l.push_back(0) ;//尾增法 
cout << "push_back()在l容器尾部添加0后输出所有元素: ";
for(auto it = l.begin();it!=l.end();++it)cout << *it << " ";
cout<<'\n' ;
l.push_front(0) ;//头增法 
cout << "push_front()在l容器首部添加0后输出所有元素: ";
for(auto it = l.begin();it!=l.end();++it)cout << *it << " ";
cout << '\n';
l.emplace_back(0) ;//尾增法 
cout << "push_emplace()在l容器尾部添加0后输出所有元素: ";
for(auto it = l.begin();it!=l.end();++it)cout << *it << " ";
cout<<'\n' ;
l.push_front(0) ;//头增法 
cout << "emplace_front()在l容器首部添加0后输出所有元素: ";
for(auto it = l.begin();it!=l.end();++it)cout << *it << " ";
cout << '\n';
cout << '\n';
} 
/*通过insert()、empplace()为list添加单个或多个元素*/ 
void test2()
{
list<int> l{1,2,3,4,5};
/*insert()*/
auto pos3= l.begin() ;
for(int i=0;i<2;++i)++pos3;//第三个元素位置迭代器 
l.insert(pos3,0) ;//单个添加 
cout << "insert()在第三个元素前添加0后输出所有元素: ";
for(auto it = l.begin();it!=l.end();++it)cout << *it << " ";
cout<<'\n' ;
pos3= l.begin() ;
for(int i=0;i<2;++i)++pos3;//第三个元素位置迭代器 
l.insert(pos3,{9,9,9}) ;//多个添加 
cout << "insert()在第三个元素前添加{9,9,9}后输出所有元素: ";
for(auto it = l.begin();it!=l.end();++it)cout << *it << " ";
cout << '\n';
pos3= l.begin() ;
for(int i=0;i<2;++i)++pos3;//第三个元素位置迭代器
l.insert(pos3,3,7) ;//n个体的方式添加 
cout << "insert()在第三个元素前添加3个7后输出所有元素: ";
for(auto it = l.begin();it!=l.end();++it)cout << *it << " ";
cout << '\n';
l.clear();//清空元素,重新测试emplace 
/*emplace()且只能添加单个元素*/
l={1,2,3,4,5};//'='重载实现直接赋值
pos3= l.begin() ;
for(int i=0;i<2;++i)++pos3;//第三个元素位置迭代器
l.insert(pos3,0) ;//只能添加单个元素 
cout << "emplace()在第三个元素前添加0后输出所有元素: ";
for(auto it = l.begin();it!=l.end();++it)cout << *it << " ";
cout << '\n';
cout << '\n';
}
/*通过splice()为list拼接链表*/ 
void test3() 
{
/*准备3个链表*/ 
list<int> l1{1,2,3} ;
list<int> l2{1,2,3} ;
list<int> l3{1,2,3} ;
/*准备3个消耗链表*/ 
list<int> t1{1,2,3} ;
list<int> t2{1,2,3} ;
list<int> t3{1,2,3} ;
/*1.splice(iterator pos, list& l)*/
l1.splice(++l1.begin(),t1) ;
cout << "链表t1插入到l1的第二个元素之前: ";
for(auto it = l1.begin();it!=l1.end();++it)cout << *it << " ";
cout << '\n';
/*2.splice(iterator pos, list& l, iterator i)*/
l1.splice(++l2.begin(),t2,++t2.begin()) ;
cout << "链表t2的第二个元素插入到l2的第二个元素之前: ";
for(auto it = l2.begin();it!=l2.end();++it)cout << *it << " ";
cout << '\n';
/*3.splice(iterator pos, list& l, iterator first, iterator last)*/
l1.splice(++l3.begin(),t3,++t3.begin(),t3.end()) ;
cout << "链表t3区间[first,last)内所有元素插入到l3的第二个元素之前: ";
for(auto it = l3.begin();it!=l3.end();++it)cout << *it << " ";
cout << '\n';
}
int main(){
    test1();
    test2();
    test3();
    return 0;
}

虽然比起之前序列式容器学习增加了个splice()拼接,但不影响我们归纳学习list容器。可以看到对list的元素插入也是完全没问题:

list容器插入元素

学习为list容器添加元素,贵在练习,所谓“熟能生巧”,读者也快试试通过不同成员函数为链表添加元素吧!

点赞(0)

C语言网提供由在职研发工程师或ACM蓝桥杯竞赛优秀选手录制的视频教程,并配有习题和答疑,点击了解:

一点编程也不会写的:零基础C语言学练课程

解决困扰你多年的C语言疑难杂症特性的C语言进阶课程

从零到写出一个爬虫的Python编程课程

只会语法写不出代码?手把手带你写100个编程真题的编程百练课程

信息学奥赛或C++选手的 必学C++课程

蓝桥杯ACM、信息学奥赛的必学课程:算法竞赛课入门课程

手把手讲解近五年真题的蓝桥杯辅导课程

Dotcpp在线编译      (登录可减少运行等待时间)