返回完整目录

1.2 模板实参推断 Template Argument Deduction

当调用函数模板(如max())时,模板参数由传入的实参决定。如果传递两个int给参数类型T,C++编译器推断出T的类型为int。

然而,T可能是类型的一部分。比如说,如果声明max()使用常量引用(const reference):

template <typename T>
T max(T const& a, T const& b)
{
return b < a ? a : b;
}

并且传递int类型的参数,T同样被推断为int类型,因为函数参数与int const&完全匹配。

类型推断时类型转换

在类型推断中,自动类型转换受到限制:

  • 当声明调用参数(call parameter)为引用类型,甚至一般的转换也不能用于类型推断。两个声明为同一个模板参数(template parameter)T类型的实参必须严格匹配。(Two arguments declared with the same template parameter T must match exactly)。

  • 当声明调用参数为值类型,只有退化(decay)的普通转换才被支持。const或者volatile等限制将被忽略,引用类型转化为被引用的类型,原始数组(raw array)或者函数被转化为对应的指针类型。两个被声明为同一个模板参数T类型的实参,其退化类型必须匹配。

比如:

template <typename T>
T max(T a, T b);
...
int i = 17;
int const c = 42;
max(i, c); //OK: T 被推断为int
max(c, c); //OK: T 被推断为int
int& ir = ;
max(i, ir); //OK: T被推断为int
int arr[4];
max(&i, arr); //OK: T被推断为int*

然而,以下调用将引发错误:

max(4, 7.2);      //Error:T 可能被推断为int或者double
std::string s;
max("hello", s); //Error: T 可能被推断为char const[6]或者std::string

有三种方法来处理此类错误:

  1. 转换实参使得两个参数得以匹配:
max(static_cast<double>(4), 7.2);
  1. 显式指定或者限制T的类型来防止编译器进行类型推断:
max<double>(4, 7.2);
  1. 将两个参数指定为不同的类型。

第1.3节将围绕该方案,第7.2节和第15章将详细讨论类型推断过程中的类型转换规则。

默认实参的类型类型推断 Type Deduction for Default Arguments

默认调用实参(default call arguments)不能用于类型推断,比如:

template <typename T>
void f(T = "");
...
f(1); //OK: T推断为int,因此它将调用f<int>(1)
f(); //Error: 无法推断T类型

为了支持这一情形,必须声明默认模板实参(default argument for the template parameter),这将在1.4节中讨论:

template <typename T = std::string>
void f(T = "");
...
f(); //OK

C++ Templates (1.2 模板实参推断 Template Argument Deduction)的更多相关文章

  1. C++ Templates (1.4 默认模板实参 Default Template Arguments)

    返回完整目录 目录 1.4 默认模板实参 Default Template Arguments 1.4 默认模板实参 Default Template Arguments 可以为模板参数定义默认值,这 ...

  2. 【C++ Primer 第16章】2. 模板实参推断

    模板实参推断:对于函数模板,编译器利用调用中的函数实参来确定模板参数,从函数实参来确定模板参数的过程被称为模板实参推断. 类型转换与模板类型参数 与往常一样,顶层const无论在形参中还是在是实参中, ...

  3. C++学习笔记(4)----模板实参推断

    1. 如图所示代码,模板函数 compare(const T&, const T&) 要求两个参数类型要一样. compare("bye","dad&qu ...

  4. C++ Templates(1.3 多模板参数 Multiple Template Parameters)

    返回完整目录 目录 1.3 多模板参数 Multiple Template Parameters 1.3.1 为返回类型设置模板参数参数 Template Parameters for Return ...

  5. [Effective Modern C++] Item 1. Understand template type deduction - 了解模板类型推断

    条款一 了解模板类型推断 基本情况 首先定义函数模板和函数调用的形式如下,在编译期间,编译器推断T和ParamType的类型,两者基本不相同,因为ParamType常常包含const.引用等修饰符 t ...

  6. 现代C++之理解模板类型推断(template type deduction)

    理解模板类型推断(template type deduction) 我们往往不能理解一个复杂的系统是如何运作的,但是却知道这个系统能够做什么.C++的模板类型推断便是如此,把参数传递到模板函数往往能让 ...

  7. C++ template —— 实例化和模板实参演绎(四)

    本篇讲解实例化和模板实参演绎-------------------------------------------------------------------------------------- ...

  8. ES - Index Templates 全局index模板

    1.Index Templates 之前我们聊过Dynamic template,它作用范围是特定的Index,如果我们想针对全局Index进行设置该如何操作呢? Index Templates 可以 ...

  9. C++中decltype(*)作为模板实参时的隐藏问题

    在函数模板中使用智能指针时,可能会希望根据指针的类型推导出指针引用的对象类型作为模板参数,于是写出以下代码: shared_ptr<decltype(*objPtr)>(objPtr); ...

随机推荐

  1. leetcode题库练习_左旋转字符串

    题目:左旋转字符串 字符串的左旋转操作是把字符串前面的若干个字符转移到字符串的尾部.请定义一个函数实现字符串左旋转操作的功能.比如,输入字符串"abcdefg"和数字2,该函数将返 ...

  2. RHEL7配置ip地址

    通过修改ifcfg-eno16777728配置文件来修改配置ip 网卡命令格式:eno16777728 en:代表enthernet(以太网) o:代表onboard(内置) 16777728:是主板 ...

  3. Redis系列(九):Redis的事务机制

    提到事务,相信大家都不陌生,事务的ACID四大特性,也是面试时经常问的,不过一般情况下,我们可能想到的是传统关系型数据库的事务,其实,Redis也是提供了事务机制的,本篇博客就来讲解下Redis的事务 ...

  4. __new__方法理解

    class Foo(object): def __init__(self, *args, **kwargs): pass def __new__(cls, *args, **kwargs): retu ...

  5. PHP strftime() 函数

    ------------恢复内容开始------------ 实例 根据区域设置格式化本地日期和时间: <?php echo(strftime("%B %d %Y, %X %Z&quo ...

  6. PHP strncmp() 函数

    实例 比较两个字符串(区分大小写): <?php高佣联盟 www.cgewang.comecho strncmp("Hello world!","Hello ear ...

  7. 【Canal】互联网背景下有哪些数据同步需求和解决方案?看完我知道了!!

    写在前面 在当今互联网行业,尤其是现在分布式.微服务开发环境下,为了提高搜索效率,以及搜索的精准度,会大量使用Redis.Memcached等NoSQL数据库,也会使用大量的Solr.Elastics ...

  8. GLIBC_2.18 not found 之类的问题解决办法

    先到 /usr/lib64 下 ll libstdc++* 会发现 libstdc++.so.6 指向了一个新的.比如我这里之前指向6.0.22这个版本,报错 此时只要重新建立软连接 将软连接指向旧的 ...

  9. Spring bean作用范围

    1,singleton Spring ioc 容器中仅有一个 Bean 实例,Bean 以单例的方式存在:2,prototype 每次从容器中调用 Bean 时,都返回一个新的实例:3,request ...

  10. Apache Hudi + AWS S3 + Athena实战

    Apache Hudi在阿里巴巴集团.EMIS Health,LinkNovate,Tathastu.AI,腾讯,Uber内使用,并且由Amazon AWS EMR和Google云平台支持,最近Ama ...