跳至正文

读书笔记《现代C++语言核心特性解析》 | 前五章

介绍

是一本介绍C++11到C++20特性的书籍。
越来越多的项目迁移到了更新的标准上,毕竟带来了新的好用的特性,而且性能依然非常的高,需要学习一下。

不会大而全的记录,主要会是让我有所醒悟的内容。

基础类型

整型

新增了long long表示至少64位的整数,对应的还有LL和ULL的后缀。

long long x = 65536LL;
unsigned long long x = 65536ULL;

整型上限:

std::numeric_limits<long long>::min()
std::numeric_limits<long long>::max()
std::numeric_limits<unsigned long long>::max()

字符和字符串

字符集和编码方法

字符集和编码方法是有区别的,字符集就是所有字符的集合,应该是包含所有的文字对应的图像,而编码方式就是用数字和字符集建立对应关系的方法。
Unicode有三种编码方式,UTF-8, UTF-16, UTF-32,都是Unicode字符集。而UTF-X是具体的编码方式,UTF-32是最简单的,用4个字节直接存储一个字符,但是很浪费。UTF-16稍微好一点,UTF-8特别差,不好计算长度不好查找字符。

标准新增类型

新增了char16_t和char32_t,分别用来对应Unicode字符集的UTF-16和UTF-32两种编码方法。

  • utf8的前缀u8
  • utf16的前缀u
  • utf32的前缀U
  • wchat_t的前缀是L(早期定义的类型)
char utf8c = u8'a';       // C++17标准
char16_t utf16c = u'好';
char32_t utf32c = U'好';

在C++11标准中u8只能作为字符串字面量的前缀,而无法作为字符的前缀。这个问题直到C++17标准才得以解决,所以上述代码需要C++17的环境来执行编译。

whcar_t是早期定义的类型,没有严格规定大小,导致Windows是16位,Linux是32位,这种标准不好修改,所以引入新的标准解决这个问题。

新增的函数,记忆主要是分三个类型:

  • mbr: utf-8,即char
  • c16: utf-16
  • c32: utf-32
    size_t mbrtoc16(char16_t * pc16,const char * s,size_t n,mbstate_t * ps);
    std::mbrtoc32
    std::c16rtomb
    std::c32rtomb

    auto

    主要的用法有两个:

  • 声明变量时2,自动推断类型
  • 声明函数时返回值的占位符(模板推导使用)

还有几个要点:

  • 从左到右推导
  • 不会收窄类型
  • 总是使用更强的类型
  • 无法声明非静态成员变量
  • 按值推导会忽略cv限定符、引用属性
  • 使用auto和万能引用声明变量,左值会被推导为引用
  • 如果目标对象是数组或者函数,auto会推导为对应的指针类型

T &&是万能引用声明,会触发引用折叠。

decltype

这个初步了解的话,比较清楚地是:

int i = 1;
decltype(i) j = 2;      // 推到为int

但是它的复杂之处就在于它的推导,auto是将cv去掉了,而且不主动用万能引用引发引用折叠是不会有太多引用的问题要考虑的。

但是decltype的推倒过程是要考虑引用的,它整体的推导规则:
decltype(e) 其中e的类型是T,推导规则有五条:

  1. 如果e是未加括号的符号表达式或者未加括号的类成员访问,则推出的类型是T;
  2. 如果e是一个函数调用或者仿函数调用,那么推导出返回值的类型;
  3. 如果e是一个类型为T的左值,则decltype(e)是T&
  4. 如果e是一个类型为T的将亡值,则decltype(e)是T&&
  5. 除了以上情况,推导结果为T

但是实际实验,发现在创造的时候由不符合这个情况,可能是因为编译不过就自动退化了。

其他资料

字符编码那些事

End.

发表回复

您的电子邮箱地址不会被公开。 必填项已用 * 标注

目录