百科问答小站 logo
百科问答小站 font logo



C++ 的常量后缀在什么情况下使用? 第1页

  

user avatar   peter-43-43-80 网友的相关建议: 
      

看了下现在已经有的回答,都没有拎出这个语法现象的本质。实际上,常量后缀语法只是对常量进行强制类型转化的语法糖而已。

C 语言的语法比较简单纯粹,所以我们先来举几个 C 语言里的例子

       void g(unsigned long long);  void f(int i) {     g(2333ull * i % 100000007ull); }      

相信很多人都见过这样的代码,事实上,这种模式的代码在线性同余的算法中很常见。为何这一行代码不直接写为 2333 * i %100000007 呢?

因为我们知道,C 中的整型运算是封闭的,即两个 int 型数做加减乘除取余运算以后,结果仍是一个 int 型数。那么当两个比较大的整型数做乘法运算,结果可能发生溢出时,如若想保留精确的运算结果,则必须将其中一位提前转换成长整数再参与运算,也即:

       voidf(int i) {     g((unsigned long long)(2333)* i % (unsigned long long)(100000007ull)); }      

试问这么长的表达式你是否喜欢?

同样的,对于浮点数也有类似的道理。C 中,如若直接写小数字面常量,比如 3.14,则默认是 double 类型的,有时我们不需要这么高的精度,只需要保留 float 的精度即可,那么你可以选择写成 (float)(3.14),当然也可以写作 3.14f。

至此,一切已明了。常量后缀只是对常量做强制类型转换的语法糖。

===============================

C++11 以后对这个语法规则做了扩充,不但扩充了常量前缀(和后缀是一个道理),还支持了用户自定义常量后缀。我们不妨再举一些例子。

譬如在新增的前缀中,u8'a' 可用于表示 UTF8 编码的字符;u'汉' 可用于表示 UTF-16 编码的字符,它和 (char16_t)('汉') 是一个道理。

用户自定义常量后缀里,以 chrono 库中对时长的重载最得精髓。

       std::this_thread::sleep_for(10ns); // 休眠 10 纳秒 std::this_thread::sleep_for(10us); // 休眠 10 微秒 std::this_thread::sleep_for(10ms); // 休眠 10 毫秒 std::this_thread::sleep_for(10s); // 休眠 10 秒 std::this_thread::sleep_for(10min); // 休眠 10 分钟 std::this_thread::sleep_for(1h + 10min + 20s); // 休眠 1 小时 10 分钟 20 秒      

其中最后一句是和

       std::this_thread::sleep_for(std::chrono::hours(1) + std::chrono::minutes(10) + std::chrono::seconds(20));      

是等价的,请问你喜欢哪种?

再比如,对字符串的字面量后缀重载:

       std::cout << (std::string("Hello") + std::string("world")).length() << std::endl;      

       std::cout << ("Hello"s + "world"s).length() << std::endl;      

比,你觉得怎么样?

最后再来一组即将到来的 C++20 中,对日期的支持:

       auto date = 2019y / 8m / 7d; std::cout << "today is: " << date << std::endl;      

最后再给题主一个建议,学 C/C++ 靠的不是死记硬背,不是背下了什么什么语法就是会这么语言了。你必须去理解各个语法现象背后的本质!理解不了就证明你代码写少了,多写点什么东西走过些弯路、踩过些坑自然就明白了。




  

相关话题

  C++中,自定义函数写在main之前更好,还是之后更好? 
  为什么大学不教javaScript? 
  有个人说C++程序入口是mainCRTStartup,另一个人说是main,然后打起来了,如何评理? 
  为什么 Go 和 Rust 常提供静态编译好的 Linux 程序,而 C 不行? 
  如何滴水不漏的学完C语言? 
  为什么 Go 语言把类型放在后面? 
  C++ 和Java 的 double 类型都是 8 字节,为何 C++ 存不下 3.1415926 ? 
  学C#后还有必要学C语言吗? 
  C/C++ 标准库为什么不支持直接删除一个文件中的部分内容? 
  为什么大多数人用C++时都要用&&,||和!来表示与或非,而不是用and or not? 

前一个讨论
老公愚孝,该不该离婚?
下一个讨论
如何激怒一位地理学爱好者?





© 2024-09-19 - tinynew.org. All Rights Reserved.
© 2024-09-19 - tinynew.org. 保留所有权利