C++模板中const int与int的不同重载匹配行为问询
C++函数模板重载匹配行为解析
先明确两个函数模板的签名:
// 模板1:第一个参数固定为const int&,第二个为任意非const左值引用 template<class f0> void func(const int& a1, f0& a2); // 模板2:两个参数均为任意非const左值引用 template<class f0, class f1> void func(f0& a1, f1& a2);
模板重载决议的核心规则:
- 优先选择更特化的模板(当两个模板都可行时)
- 非const左值引用(
T&)无法绑定右值(临时对象),而const左值引用(const T&)可以绑定右值、const左值、非const左值
下面逐个分析你的调用场景:
1. func(static_cast<const int &>(bb), bbb)
第一个参数是const int&类型的左值,两个模板都可行:
- 模板1:直接匹配第一个参数,
f0推导为int(匹配bbb的int&) - 模板2:
f0推导为const int,f1推导为int
由于模板1对第一个参数的匹配更特化(固定为const int&,而非模板2的通用引用),因此优先选择模板1,输出6。
2. func(bb, bbb)
两个参数都是int类型的非const左值:
- 模板2:
f0推导为int,f1推导为int,完全匹配(无需任何类型转换) - 模板1:第一个参数需要将
int&转换为const int&(虽然合法,但属于隐式转换)
模板2的匹配更精确(无转换),因此被选中,输出0。
3. func((int)bb, bbb)
(int)bb是临时右值:
- 模板2的第一个参数是
f0&(非const左值引用),无法绑定右值,因此模板2不可行 - 模板1的第一个参数
const int&可以绑定右值,f0推导为int匹配bbb,因此只能选择模板1,输出6。
4. func(static_cast<int &>(bb), bbb)
第一个参数是int&类型的非const左值,和场景2完全一致,模板2完全匹配,输出0。
5. func(static_cast<int>(bb), bbb)
static_cast<int>(bb)是临时右值,和场景3一致:模板2无法绑定右值参数,只能选择模板1,输出6。
内容的提问来源于stack exchange,提问作者alimadodo
相关产品推荐
相关产品推荐

