c++字面量
发展
自C++11以来添加了多线程模型,函数式编程功能等

字面量
基础数据类型都有字面量值,字面量值是固定的,也称为常量:
int unsigned_int = u'U'; // Unsigned integer
int hex = 0x2a; // Hexadecimal
std::string raw = R"(Raw String)"; // Raw string
lambda
表达式是函数字面量:
[](int a, int b){ return a+b; }
Raw字符串
例如R"(Raw String)"
写法,原始字符串,无视转义;对于路径表达式或者正则表达式很有用。注意:raw string可以跨越多行,其中的空白和换行符都属于字符串的一部分
raw字符串可以使用空串或者不超过16字符串(不含空格,反斜线)
作为raw字符串的delimiter:
std::string raw = R"delimiter(Raw String)delimiter"
使用()
和分隔字符串主要是为了使raw字符串可以更好包含“
自定义字面量
C++11允许自定义字面量(解释含义/实际类型),通过给整型、浮点型、字符、C字符串加后缀和自定义操作符函数实现
- 语法
1010_b // Natural numbers
123.45_km // Floating point numbers
"hello"_i18n // C-string literals
'1'_character // Character literals
<built_in-Literal>_<Suffix>
- 实现
literal operator
,运行时将用户定义的字面量映射到对应的函数结果
int operator"" _b(unsigned long long bin) //C++14中函数中_b前没有空格
{
return 3;
}
作用:用户定义字面量到运算符的自动映射,可以实现类型安全算术,如编译器确保不可能将苹果和梨想加。
注意:如果是-100_b
运算符的参数只会使用解析的100,返回的数字再和-
运算为负数
C++14内置的字面量
C++14包含一些二进制数字、C++字符串、复数、时间单位的字面量,内置语法中只有前缀或后缀不加_
:

- 过去C++ 只支持 C 字符串字面量,必须始终使用 C 字符串(char [])来初始化 C++ 字符串;C++14 中,第一次支持字符串类型字面量
- 使用字符串字面量,需要
using namespace std::literals;
- 时间字面量属于类型
std::chrono::duration
,需要using namespace std::literals::chrono_literals;
- 时间字面量支持基本的加法、减法、乘法、除法和模运算
2种自定义字面运算符
raw运算符
接收参数(const char*, size_t)
,(const char*)
orconst char
cooked运算符
接收参数(long double)
,(unsigned long long int)
只有raw literal operators
形式的运算符才可以处理C语言形式字面字符串和字符,总结:

- 除了
char
数据类型,C ++支持的数据类型wchar_t
,char16_t
和char32_t
,可以使用这些类型作为C字符串的底层类型(图中举例char
) - 对数整型或浮点数,如果同时实现两个版本,编译器将选择
Cooked形式
,它具有更高的优先级 - 如果使用long double运算符,整型字面量则不能调用,需要进行重载才可以
函数签名总结

例子
举例说明内置时间字面量的用法,例如s(seconds)
,m(minute)
,h(hours)
等都是std:chrono::duration
类型对象:
/// milliseconds
using milliseconds = duration<_GLIBCXX_CHRONO_INT64_T, milli>;
/// seconds
using seconds = duration<_GLIBCXX_CHRONO_INT64_T>;
/// minutes
using minutes = duration<_GLIBCXX_CHRONO_INT64_T, ratio< 60>>;
/// hours
using hours = duration<_GLIBCXX_CHRONO_INT64_T, ratio<3600>>;
#if __cplusplus > 201703L
/// days
using days = duration<_GLIBCXX_CHRONO_INT64_T, ratio<86400>>;
...
#endif // C++20
#include <chrono>
#include <iostream>
using namespace std::literals::chrono_literals;
int main() {
std::cout << std::endl;
typedef std::chrono::duration<long long, std::ratio<2700>> hour;
auto schoolHour = hour(1);
// auto schoolHour= 45min;
auto shortBreak = 300s;
auto longBreak = 0.25h;
auto schoolWay = 15min;
auto homework = 2h;
auto schoolDayInSeconds = 2 * schoolWay + 6 * schoolHour + 4 * shortBreak + longBreak + homework;
std::cout << "School day in seconds: " << schoolDayInSeconds.count() << std::endl;
std::chrono::duration<double, std::ratio<3600>> schoolDayInHours = schoolDayInSeconds;
std::chrono::duration<double, std::ratio<60>> schoolDayInMinutes = schoolDayInSeconds;
std::chrono::duration<double, std::ratio<1, 1000>> schoolDayInMilliseconds = schoolDayInSeconds;
std::cout << "School day in hours: " << schoolDayInHours.count() << std::endl;
std::cout << "School day in minutes: " << schoolDayInMinutes.count() << std::endl;
std::cout << "School day in milliseconds: " << schoolDayInMilliseconds.count() << std::endl;
std::cout << std::endl;
}