本章主要介绍了标准库中的string、vector和bitset类型。
一、命名空间的using声明
使用using声明可以在不需要加前缀namespace_name::的情况下访问命名空间中的名字。using声明的形式如下:
using namespace::name;
一旦使用using声明,我们可以直接引用名字,而不需要再引用该名字的命名空间。如:
#include <iostream>
#include <string>
int main(int argc, char** argv)
{
using std::string;
using std::cin;
using std::cout;
string sum;
int x, y;
// endl没有通过using声明则必须加std::命名空间前缀
cout << "please input two numbers\n" << std::endl;
cin >> x;
cin >> sum;
cin >> y;
cout << "Result: " << x << sum << y << "=" << x + y << std::endl;
return 0;
}
二、 标准库string函数
string类型是C里面没有的, C++为了强化字符串的操作,专门为其设定的一个string类
比如 C语言里一般用 char *str;表示一个字符串,要拷贝字符串的时候要用函数
strcpy(str1,str2);
但是string类可以直接相加
str=str1+str2;
也就是说string里面重载了很多对字符串的操作, 而不是单一的把字符串放入内存这么简单了。
几种初始化string的方式:
string s1; 默认构造函数 s1 为空串
string s2(s1); 将 s2 初始化为 s1 的一个副本
string s3("value"); 将 s3 初始化为一个字符串字面值副本
string s4(n, 'c'); 将 s4 初始化为字符 'c' 的 n 个副本
常用的string对象操作:
s.empty() 如果 s 为空串,则返回 true,否则返回 false。
s.size() 返回 s 中字符的个数
s[n] 返回 s 中位置为 n 的字符,位置从 0 开始计数
s1 + s2 把 s1 和 s2 连接成一个新字符串,返回新生成的字符串
s1 = s2 把 s1 内容替换为 s2 的副本
v1 == v2 比较 v1 与 v2 的内容,相等则返回 true,否则返回 false
!=, <, <=, >, >= 保持这些操作符惯有的含义
string::size_type类型
从逻辑上来讲,size() 成员函数似乎应该返回整形数值,或无符号整数。但事实上,size 操作返回的是 string::size_type 类型的值。string 类类型和许多其他库类型都定义了一些配套类型(companion type)。
通过这些配套类型,库类型的使用就能与机器无关(machine-independent)。size_type就是这些配套类型中的一种。它定义为与 unsigned 型(unsigned int 或 unsigned long)具有相同的含义,而且可以保证足够大能够存储任意 string 对象的长度。
不要把str.size()的返回结果赋值给一个ini型。
string对象中字符的处理<cctype>头文件中
isalnum(c) 如果 c 是字母或数字,则为 True。
isalpha(c) 如果 c 是字母,则为 true。
iscntrl(c) 如果 c 是控制字符,则为 true
isdigit(c) 如果 c 是数字,则为 true。
isgraph(c) 如果 c 不是空格,但可打印,则为 true。
islower(c) 如果 c 是小写字母,则为 true。
isprint(c) 如果 c 是可打印的字符,则为 true。
ispunct(c) 如果 c 是标点符号,则 true。
isspace(c) 如果 c 是空白字符,则为 true。
isupper(c) 如果 c 是大写字母,则 true。
isxdigit(c) 如果是 c 十六进制数,则为 true。
tolower(c) 如果 c 大写字母,返回其小写字母形式,否则直接返回 c。
toupper(c) 如果 c 是小写字母,则返回其大写字母形式,否则直接返回 c。
C 标准库头文件命名形式为 name 而 C++ 版本则命名为 cname ,少了后缀,.h 而在头文件名前加了 c 表示这个头文件源自 C 标准库。cname 头文件中定义的名字都定义在命名空间 std 内,而 .h 版本中的名字却不是这样。建议:采用C 标准库头文件的C++ 版本
三、 标准库vector类
vector 是同一种类型的对象的集合,每个对象都有一个对应的整数索引值。和 string 对象一样,标准库将负责管理与存储元素相关的内存。我们把 vector 称为容器,是因为它可以包含其他对象。一个容器中的所有对象都必须是同一种类型的。
vector 是一个类模板,可用来定义任意多种数据类型。vector 类型的每一种都指定了其保存元素的类型。因此,vector<int> 和 vector<string> 都是数据类型。如:
vector<int> ivec; // ivec holds objects of type int
vector<Sales_item> Sales_vec; // holds Sales_items Class'object
vector对象的定义和初始化
vector<T> v1; vector 保存类型为 T 对象。 默认构造函数 v1 为空。 不含任何元素。
vector<T> v2(v1); v2 是 v1 的一个副本。
vector<T> v3(n, i); v3 包含 n 个值为 i 的元素。
vector<T> v4(n); v4 含有值初始化的元素的 n 个副本。
如果没有指定元素的初始化式,那么标准库将自行提供一个元素初始值进行值初始化(value initializationd)。这个由库生成的初始值将用来初始化容器中的每个元素,具体值为何,取决于存储在 vector 中元素的数据类型。
vector<string> fvec(10); // 10 elements, each initialized to 0
vector<string> svec(10);// 10 elements, each an empty string
vector对象的操作
v.empty() 如果 v 为空,则返回 true,否则返回 false。
v.size() 返回 v 中元素的个数。 返回值类型: vector<T>::size_type
v.empty() 如果 v 为空,则返回 true,否则返回 false。
v.push_back(t) 在 v 的末尾增加一个值为 t 的元素。
v[n] 返回 v 中位置为 n 的元素。
v1 = v2 把 v1 的元素替换为 v2 中元素的副本。
v1 == v2 如果 v1 与 v2 相等,则返回 true。
!=, <, <=, >, >= 保持这些操作符惯有的含义。
下标操作不添加元素
初学 C++ 的程序员可能会认为 vector 的下标操作可以添加元素,其实不然:
vector<int> ivec; // empty vector
for (vector<int>::size_type ix = 0; ix != 10; ++ix)
ivec[ix] = ix; // disaster: ivec has no elements
这个循环的正确写法应该是:
for (vector<int>::size_type ix = 0; ix != 10; ++ix)
ivec.push_back(ix);// ok: adds new element with value ix
必须是已存在的元素才能用下标操作符进行索引。通过下标操作进行赋值时,不会添加任何元素。
四、 迭代器简介
除了使用下标来访问 vector 对象的元素外,标准库还提供了另一种访问元素的方法:使用迭代器(iterator)。迭代器是一种检查容器内元素并遍历元素的数据类型。
标准库为每一种标准容器(包括 vector)定义了一种迭代器类型。迭代器类型提供了比下标操作更通用化的方法:所有的标准库容器都定义了相应的迭代器类型,而只有少数的容器支持下标操作。因为迭代器对所有的容器都适用,现代 C++ 程序更倾向于使用迭代器而不是下标操作访问容器元素,即使对支持下标操作的 vector 类型也是这样。
窗口的iterator类型
每一种容器都定义了自己的iterator类型,如vector:
vector<int>::iterator iter;
每个标准库容器类型都定义了一个名为iterator的成员。
begin和and操作
vector<int> ivec(10);
vector<int>::iterator iter = ivec.begin();
此时iter指向ivec[0]。由end操作返回的迭代器指向vector的‘末端元素的下一个’。通常称为超出末端迭代器,表明它指向了一个不存在的元素。如果vector为空,begin返回的迭代器与end返回的迭代器相同。
vector迭代器的自增和解引用运算
++iter; //自增
*iter 等价于 iter[0]
由于end操作返回的迭代器不指向任何元素,因此不能对它进行解引用或自增操作。
另一对可执行于迭代器的操作就是比较,用==或!=操作符来比较两个迭代器,如果两个迭代器指向同一元素则相等,否则就不相等。
// equivalent loop using iterators to reset all the elements in ivec to 0
for (vector<int>::iterator iter = ivec.begin();
iter != ivec.end(); ++iter)
// set element to which iter refers to 0
*iter = 0;
每种容器类型还定义了一种名为 const_iterator 的类型,该类型只能用于读取容器内元素,但不能改变其值。
五、 标准库bitset类型
略