C++98/03拾遗
const
关键字
常量修饰符
const
变量不再允许延迟赋值,必须于声明时赋值.
1 | const int MAX_VALUE; // ERROR! |
而下例是允许的,因为其是指向常整型的指针变量.
1 | const int* pt; |
而指向整型变量的常指针的声明如下.
1 | int *const pt; |
对于迭代器而言则如下.
const iterator
允许改变迭代器所指之物的值,但不允许指向其他东西;1
++it; // ERROR!
const_iterator
不允许改变迭代器所指之物的值,但允许指向其他东西.1
*cIt = 0; // ERROR!
const
成员函数
Physical Constness
不得更改对象之任何非static
成员变量,又称Bitwise Constness.
Physical const is stronger than logical const; if an operation is physically const it is also logically const.
Logical Constness
允许在客户端侦测不出得情况下修改对象.
mutable
是与const
成员函数相关的摆动场,用于声明允许const
成员函数更改的成员变量.
1 | private: |
当
const
成员函数和非const
成员函数有着实质等价的实现时,令非const
版本调用const
版本以避免代码重复.
数组的引用
C++中没有「引用的数组」(array of reference),形如int&a[N]
将非法.
ERROR: declaration of 'a' as array of references.
但有“数组的引用”,形如int(&a)[N]
,其作用之一是防止数组退化为指针.
下例的
&
是必须的,否则会产生编译期错误,原因是纯粹的auto推断使引用信息丢失.
1 | int a[2][3] = { 0, 1, 2, 3, 4, 5 }; |
「数组的引用」还能与模板一同发挥作用. 1
2
3
4template<typename T, int N>
void sort(T(&a)[N]) { ... }
...
sort(a);
复制和赋值
1 | Box b1; |
指向成员函数的指针
通过&
创建,访问时使用.*
或->*
.
下例中
&A::func
的&
有时能省略.而在Visual Studio 2015/2017中,省略&
将会报错.
A::func
:非标准语法.请使用&
来创建指向成员的指针.
1 | A a; |
共有友元函数
1 | class B; // 必须前置声明 |
特殊的运算符重载
仿函数(Functor; operator()
)
又称伪函数.使用仿函数的示例见此.
operator new
和new
1 | class A { |
输出如下.
1 | operator new() |
总结如下.
new
=operator new
+ 构造;delete
= 析构 +operator delete
两种类型的operator[]
1 | // const对象 |
避免代码重复的操作如下.
1 | // 非const对象 |
自增/自减运算符
1 | A & A::operator++() { // 前缀 |
流运算符
返回引用是因为
istream
和ostream
不允许拷贝.
1 | friend istream & operator>>(istream & in, A & a); |
其他
不允许重载的运算符有成员访问运算符.
、成员指针访问运算符.*
、域运算符::
、三元条件运算符?:
和sizeof
运算符.
重载箭头运算符operator->
的方式如下.
1 | A* operator->() { return this; } |
重载&&
和||
运算符,并不能复现短路求值的规则.
定位new(Placement new)
需包含如下头文件.
1 |
在已分配的内存空间上实施构造,释放时不使用delete
.
1 | class A { |
模板的实例化和特化
(显式/强制)实例化;
1
template class A<TYPE>;
(显式)特化/具体化.
1
template<> class A<TYPE> { ... };
谓词(Predicate)
谓词共计三类如下.
- 函数/函数指针谓词;
- lambda表达式谓词;
- 仿函数谓词.
带捕获列表的lambda不可以隐式转换为函数指针.
1 | void (*ptr)(int) = [&](int) { }; // ERROR! |
统一三类谓词的函数参数传递方式如下.
标准库实现;
1
2template<typename Pred>
void fun(Pred p) { ... }使用
function
.需包含如下头文件.
1
1
void fun(function<bool(...)> p) { ... }
使用function
获取类成员函数如下例.
下例的
const
仅当f
为const
函数时需要,而f
为类静态成员函数时,则不需要cosnt A &
类型的第一个参数.
1 | function<void(const A &, ...)> func = &A::f; |
数字—字符串的转换
需包含如下头文件.
1 |
数字转字符串如下例.
若重复利用同一个
stringstream
对象,需要调用clear()
,否则将引发错误.
1 | stringstream ss; |
stringstream
也可实现字符串到数字的转换.