采用何种工具来查看型别推导结果,取决于你在软件开发过程的哪个阶段需要该信息。主要研究三个可能的阶段:撰写代码阶段、编译阶段、运行时阶段。

  IDE编译器

  IDE中的代码编译器通常会在你将鼠标指针选停止某个程序实体,如变量、形参、函数等时,显示出该实体的型别。例如以下这段代码:

const int theAnswer = ;
auto x = theAnswer;
auto y = &theAnswer;

  IDE编译器很可能会显示出,x的型别推导结果是int,而y则是const int*。

  而让这种方法奏效,代码就多多少少要处于一种可编译状态。因为让IDE提供此类信息的工作原理是让C++编译器(或至少也是其前端)在IDE内执行一轮。如果该编译器不能在分析你的代码时得到足够的有用信息,自然也就无法显示出推导除了何种型别。

  对于像int这样的平凡型别,从IDE能得到的信息大体良好。不过你很快就会看到,一旦较为复杂的型别现身,IDE显示的信息就不太有用了。

  编译器诊断信息

  想要让编译器显示其推导出的型别,一条有效的途径是使用该型别推导某些编译错误。而报告错误的消息几乎肯定会提及导致该错误的型别。

  

  运行时输出

  Boost的TypeIndex库(常写作Boost.TypeIndex),虽说该库不是C++的一部分,但IDE和像TD这样的模板也不是。Boost库(可从boost.com获得)的好处还不止于此,他跨平台、开源。这样一来,Boost库和那些依赖标准库的代码有几乎同样的可移植性。

  下面介绍一下函数f是如何在使用Boost.TypeIndex的条件下产生精确的型别信息的:

#include <boost/type_index.hpp>

template<typename T>
void f(const T& param)
{
using std::cout;
using boost::typeindex::type_id_with_cvr; //显示T的型别
cout << "T = "
<< type_id_with_cvr<T>().pretty_name()
<< '\n'; //显示param的型别
cout << "param = "
<< type_id_with_cvr<decltype(param)>().pretty_name()
<< '\n';
....
}

  这种方法的工作原理是函数模板boost::typeindex::type_id_with_cvr接受一个型别实参(我们想要获取信息的型别),而且不会移除const、volatile和引用饰词(这也是改模板的名字中为什么含有with_cvr字样),该函数模板返回一个boost::typeindex::type_index对象,它利用成员函数pretty_name产生一个包含人类可读的型别表示的std::string。

std::vector<Widget> createVec();    //工厂函数

const auto vw = createVec();         //使用工厂函数返回值初始化vw

if(!vw.empty()) {
f(&vw[]); //调用f
...
}

  在使用GNU和Clang编译器的情况下,Boost.TypeIndex产生了以下的(精准)输出:

T =     Widget const*
param = Widget const* const&

  微软编译器取得的结果本质上完全相同:

T =     class Widget const*
param = class Widget const* const&

  请记住无论是IDE编译器、编译器错误消息,还是像Boost.TypeIndex这样的库都仅仅是你弄明白你的编译器推导所得型别的辅助工具。他们都十分有用,但是说到底,理解条款1~条款3的型别推导知识这一点无可替代。

要点速记:

1、利用IDE编译器,编译器错误消息、和Boost.TypeIndex库常常能够查看到推导而得的型别。

2、有些工具产生的结果可能会无用,或者不准确。所以,理解C++型别推导规则是必要的。

Effective Modern C++ 条款4:掌握查看型别推导结果的方法的更多相关文章

  1. Effective Modern C++ ——条款6 当auto型别不符合要求时,使用带显式型别的初始化物习惯用法

    类的代理对象 其实这部分内容主要是说明了在STL或者某些其他代码的容器中,在一些代理类的作用下使得最后的返回值并不是想要的结果. 而他的返回值则是类中的一个容器,看下面的一段代码: std::vect ...

  2. Effective Modern C++ 条款2:理解auto型别推导

    在条款1中,我们已经了解了有关模板型别的推导的一切必要知识,那么也就意味着基本上了解了auto型别推导的一切必要知识. 因为,除了一个奇妙的例外情况,auto型别推导就是模板型别推导.尽管和模板型别推 ...

  3. Effective Modern C++ ——条款2 条款3 理解auto型别推导与理解decltype

    条款2.理解auto型别推导 对于auto的型别推导而言,其中大部分情况和模板型别推导是一模一样的.只有一种特例情况. 我们先针对auto和模板型别推导一致的情况进行讨论: //某变量采用auto来声 ...

  4. Effective Modern C++ 条款3:理解decltype

    说起decltype,这是个古灵精怪的东西.对于给定的名字或表达式,decltype能告诉你该名字或表达式的型别.一般来说,它告诉你的结果和你预测的是一样的.不过,偶尔它也会给出某个结果,让你抓耳挠腮 ...

  5. Effective Modern C++ ——条款5 优先选择auto,而非显式型别声明

    条款5 对于auto ,他的好处不仅仅是少打一些字这么简单. 首先在声明的时候, 使用auto会让我们养成初始化的习惯: auto x;//编译不通过必须初始化. 再次对于auto而言,它可以让我们定 ...

  6. Effective Modern C++ ——条款7 在创建对象时注意区分()和{}

    杂项 在本条款的开头书中提到了两个细节性问题: 1.类中成员初始化的时候不能使用小括号. 如: class A { int a(0);//错误 }; 2.对于原子性类别的对象初始化的时候不能使用= 如 ...

  7. 《Effective Modern C++》翻译--条款4:了解怎样查看推导出的类型

    条款4:了解怎样查看推导出的类型 那些想要了解编译器怎样推导出的类型的人通常分为两个阵营. 第一种阵营是实用主义者.他们的动力通常来自于编敲代码过程中(比如他们还在调试解决中),他们利用编译器进行寻找 ...

  8. Effective Modern C++  条款1:理解模板型别推导

    成百上千的程序员都在向函数模板传递实参,并拿到了完全满意的结果,而这些程序员中却有很多对这些函数使用的型别是如何被推导出的过程连最模糊的描述都讲不出来. 但是当模板型别推导规则应用于auto语境时,它 ...

  9. Effective Modern C++翻译(5)-条款4:了解如何观察推导出的类型

    条款4:了解如何观察推导出的类型 那些想要知道编译器推导出的类型的人通常分为两种,第一种是实用主义者,他们的动力通常来自于软件产生的问题(例如他们还在调试解决中),他们利用编译器进行寻找,并相信这个能 ...

随机推荐

  1. java关于lombok(包括父类参数)

    java关于lombok对bean对象进行自动设置 使用说明 使用方式 注释类型 @NonNull @Data(常用) @NoArgsConstructor(常用)/@RequiredArgsCons ...

  2. Python系统(os)相关操作

    文件操作 python中常用于文件处理的模块有os,shutil等. 1 创建文件 文件的创建可以使用open()函数,如下创建一个test_file.txt的文件: >>> wit ...

  3. iOS开发系列-GCD

    概述 GCD是苹果公司为多核的并行运算提出的解决方案.全称是Grand Central Dospatch.纯C语言,提供了非常多强大的函数. GCD自动管理线程的声明周期(创建线程.调度任务.销毁线程 ...

  4. 【daydayup】ceshuChat

    时时当勉励,岁月不待人.珍惜时间伐~ 先看看项目运行的效果 这个是在本地环境打开了两个8080端口进行模拟运行的. 先放下作者的开源地址:https://github.com/ceshu/ceshuC ...

  5. thinkphp 统计查询

    在应用中我们经常会用到一些统计数据,例如当前所有(或者满足某些条件)的用户数.所有用户的最大积分.用户的平均成绩等等,ThinkPHP为这些统计操作提供了一系列的内置方法,包括: 大理石平台检定规程 ...

  6. centos7.2安装apache比较简单,直接上代码

    centos7.2安装apache比较简单,直接上代码 1.安装 yum install httpd    2.启动apache systemctl start httpd.service    3. ...

  7. vue-cli新手总结

    项目中需要用到vue-cli脚手架来搭建前端框架,对于vue小白,总结一下自己遇到的问题以及解决方案,还要学习的地方有很多. vue-cli安装下载网上有很多教程,但对于新手而言,有些地方需要自己摸索 ...

  8. 最新MySQL5.7.3.0版本安装(图文版本)

    转自:http://www.myexception.cn/mysql/1609536.html 可以从http://dev.mysql.com/downloads/下载MySQL服务器安装软件包,我下 ...

  9. swoole是如何实现任务定时自动化调度的?

    https://www.muzilong.cn/article/117 开发环境 环境:lnmp下进行试验. 框架:laravel5 问题描述 这几天做银行对帐接口时,踩了一个坑,具体需求大致描述一下 ...

  10. hdfs写并发问题

    hdfs文件写入不支持多个进程同时写入一个文件,每次只能一个FS挟持对象的人写入