C++STL顺序容器通用操作

目录

前言

一、顺序容器概述

二、通用容器操作

三、容器定义和初始化

四、赋值与swap

五、顺序容器

1.添加元素

2.访问元素

3.删除元素

总结


前言

         一个容器就是一些特定类型对象的集合。顺序容器提供了控制元素存储和访问顺序的能力。这种顺序不依赖元素的值,而是与元素加入容器时的位置相对应。


一、顺序容器概述

vector可变大小数组。支持快速随机访问,在尾部之外的位置插入或删除元素可能很慢。
deque双端队列。支持快速随机访问。在头部和尾部插入或删除元素很快。
list双向链表。只支持双向顺序访问。在任意位置插入或删除都很快。
forward_list单向链表。只支持单向顺序访问。在任何位置插入或删除都很快。
array固定大小数组。支持快速随机访问。不能添加或删除元素。
string与vector相似的容器,但专门用于保存字符。随机访问快。在尾部插入或删除速度快。

二、通用容器操作

 类别别名

iterator此容器类型的迭代其类型
const_iterator只读迭代器
size_type无符号整数类型,足够保存此容器类型最大可能容器的大小
difference_type带符号整数类型,足够保存两个迭代器之间的距离
value_type元素类型
reference元素左值类型;与value_type&含义相同
const_reference元素的const左值类型

构造函数

C c;默认构造函数,构造空容器
C c1(c2);构造c2拷贝c1
C c(b, e);构造c,将迭代器b和e指定范围内的元素拷贝到c(array不支持)
C c{a, b, c, ...};列表初始化c

赋值与swap

c1 = c2;

将c1元素替换为c2

c1 = {a, b, c, ...};将c1元素替换为列表元素(array不支持)
a.swap(b);交换a和b
swap(a,b);交换a和b

大小

c.size()c中元素数目(forward_list不支持)
c.max_size()c中可保存的最大元素数目
c.empty()若c中有元素,则返回false;否则返回true

添加/删除元素(array不支持)

c.insert(args);将args的元素拷贝进c
c.emplace(inits);使用inits构造c中的一个元素
c.erase(args);删除args指定的元素
c.clear();删除c的所有元素

获取迭代器

c.begin(), c.end()返回指向c的首元素和尾元素之后位置的迭代器
c.cbegin(), c.cend()返回const限制的迭代器

反向容器的额外成员(forward_list不支持)

reverse_iterator按逆序寻址元素的迭代器
const_reverse_iteratorconst的逆序寻址元素的迭代器
c.rbegin(), c.rend()返回指向c的尾元素和首元素之前位置的迭代器
c.crbegin(), c.crend()返回const_reverse_iterator

关系运算符

==, !=所有容器均支持
< , <=, >, >=无序关联容器不支持

三、容器定义和初始化

C c;默认构造函数

C c1(c2);

C c1 = c2;

c1初始化为c2的拷贝。c1和c2必须是相同类型。

C c{a, b, c, ...};

C c = {a, b, c, ...};

c初始化为列表中元素的拷贝。列表中的元素必须与c的元素类型相容。
C c(b, e);c初始化为迭代器b和e指定范围中的元素拷贝。
以下仅支持顺序容器,但不包括array
C seq(n)seq包含n个元素,这些元素进行了值初始化
C seq(n, t)seq包含n个初始化为值t的元素

list<string> authors = {"Milton", "Shakespeare", "Austen"};
vector<const char*> articles = {"a", "an", "the"};

list<string> list2(authors);//正确
deque<string> authlist(authors);//错误i
vector<string> words(articles);//错误
forward_list<string> words(articles.begin(), articles.end());//正确

//假定it指向authors的一个元素
deque<string> authlist(autnors.begin(), it);//正确

//与顺序容器有关的初始化
vector<int> ivec(10, -1);//10个int都是-1
list<string> svec(10, "hi!");//10个string都是"hi!"
forward_list<int> ivec(10);//10个int都是0
deque<string> svec(10);//10个string都是空

四、赋值与swap

c1 = c2将c1元素替换为c2的拷贝。c1和c2同类型
c = {a, b, c, ...}将c中元素替换为初始化列表中元素的拷贝。

swap(c1, c2)

c1.swap(c2)

交换c1和c2。c1和c2必须同类型,速度较快
assign操作不适用于关联容器和array
seq.assign(b, e)将seq的元素替换为迭代器b和e所表示范围内的元素
seq.assign(il)将seq元素替换为初始化列表il的元素
seq.assign(n, t)将seq元素替换为n个值为t的元素

//assign允许从一个不同但相容的类型赋值,或者从容器的一个子序列赋值
list<string> names;
vector<const char*> oldstyle;
names = oldstyle;//错误

names.assign(oldstyle.cbegin(), oldstyle.cend());//正确

list<string> slist(1);
slist.assign(10, "hiya!");//正确

五、顺序容器

1.添加元素

array不支持以下任何操作。

forward_list有专有的insert和emplace,且不支持push_back和emplace_back。

vector和string不支持push_front和emplace_front。

c.push_back(t)

c.emplace_back(args)

在c的尾部创建一个值为t或由args创建的元素。返回void。

c.push_front(t)

c.emplace_front(args)

在c的头部创建一个值为t或由args创建的元素。返回void。

c.insert(p, t)

c.emplace(p, args)

在迭代器p指向的元素之前创建一个值为t或由args创建的元素。返回新添加元素的迭代器。
c.insert(p, n, t)在迭代器p指向的元素之前插入n个值为t的元素。返回指向新添加第一个元素的迭代器;若n为0,则返回p。
c.insert(p, b, e)将迭代器b和e指定的范围内的元素插入到迭代器p指向的元素之前。返回指向新添加第一个元素的迭代器;若范围为空,则返回p。
c.insert(p, il)il是一个花括号包围的元素值列表。将这些给定值插入到迭代器p指向的元素之前。返回指向新添加第一个元素的迭代器;若列表为空,则返回p。

//在特定位置添加元素
vector<string> svec;
list<string> slist;

//等价slist.push_front("hello!");
slist.insert(slist.begin(), "hello!");

//vector等价push_front()形式,但速度可能很慢
svec.insert(svec.begin(), "hello!");

//插入范围内元素
//将10个anna插入到svec末尾
svec.insert(svec.end(), 10, "anna");
vector<string> v = {"qussi", "simba", "frollo", "scar"};
//将v最后两个元素添加到slist开始
slist.insert(slist.begin(), v.end()-2, v.end());
slist.insert(slist.end(), {"thses", "worsd", "will"});
slist.insert(slist.begin(), slist.begin(), slist.end());//错误,迭代器表示要拷贝范围,不能指向与目的位置相同的容器

//使用insert的返回值
list<string> lst;
auto iter = lst.begin();
while(cin >> word)
    iter = lst.insert(iter, word);//相当于调用push_front

//当调用emplace函数时,则是将参数传递给元素类型的构造函数。
c.emplace_back("hello", 25, 19.22);
//等价于
c.push_back(sales_data("hello", 25, 19.22));

2.访问元素

at和下标操作只适用于vector, string, deque, array

back不适用于forward_list

c.back()返回c尾元素的引用,若c为空,则未定义
c.front()返回c头元素的引用,若c为空,则未定义
c[n]返回c中下标为n的引用,若n>=c.size(),则未定义
c.at(n)返回下标为n元素的引用,若越界则“out of range”

if(!c.empty())
{
    c.front() = 42;//将42赋值给第一个元素
    auto &v = c.back();//获得指向最后一个元素的引用
    v = 1024;//改变c的元素
    auto v2 = c.back();//v2不是引用,他是c.back()的一个拷贝
    v2 = 0;//未改变c中的元素
}

//安全访问
vector<string> svec;
cout << svec[0];//运行错误
cout << svec.at(0);//跑出out of range 异常

3.删除元素

这些操作会改变容器的大小,因此不适用于array

forward_list有特殊版本的erase,不支持pop_back

vector和string不支持pop_front

c.pop_back()删除尾元素。若为空则未定以。返回void。
c.pop_front()删除头元素。若为空则未定以。返回void。
c.erase(p)删除迭代器p指向的元素。返回指向被删元素之后元素的迭代器,若p为伪元素,则返回尾后迭代器。若p是尾后迭代器,则未定义。
c.erase(b, e)删除迭代器b和e所指范围内的元素。返回最后一个被删元素之后元素的迭代器。若e本身是尾后迭代器,则返回尾后迭代器。
c.clear()删除c中所有元素。返回void。

if(!ilist.empty())
{
    ilist.pop_front();
}

//容器内删除元素,删除以下所有奇数
list<int> lst = {1, 2, 3, 4, 5, 6, 7, 8, 9};
auto it = lst.begin();
while(it != lst.end())
{
    if(*it %2) it = lst.erase(it);
    else ++it;
}

//删除多个元素
//elem1指向要删除的第一个元素,elem2指向要删除的最后一个元素之后的位置
elem = slist.erase(elem1, elem2);


总结

        本篇总结了STL顺序容器的常用通用操作。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值