编译器如何处理函数调用
在 C++ 中调用函数模板要经过名称查找的三位一体(标准中的第 3.4 节)、模板参数推导(第 14.8.2 节)和重载解析(第 13.3 节)。
除了阅读C++ 标准中的这些部分之外,您还可以在优秀的书籍C++ 模板:完整指南中阅读它,或者观看 Stephan T. Lavavej 的前三个核心 C++ 视频
一瞥标准
正如您自己已经发现的那样,该宏最初是在 STL 的 SGI 实现中,当时还没有 C++ 标准,编译器对函数模板的支持非常粗略。
// * __STL_FUNCTION_TMPL_PARTIAL_ORDER:如果编译器支持 // 函数模板的部分排序,则定义。(又名函数模板的部分特化 //。)
要了解函数模板的偏序是用来做什么的,这里有一个引用(如果您阅读本书并观看链接的视频,这将变得更加清晰)。
14.5.6.2 函数模板的部分排序[temp.func.order]
1如果函数模板被重载,则函数模板特化的使用可能会产生歧义,因为模板参数推导 (14.8.2) 可能将函数模板特化与多个函数模板声明相关联。在以下上下文中使用重载函数模板声明的部分排序来选择函数模板特化所引用的函数模板:
— 在调用函数模板特化 (13.3.3) 的重载决议期间;
— 当一个函数模板特化的地址被取用时;
— when a placement operator delete that is a function template specialization is selected to match a placement operator new (3.7.4.2, 5.3.4);
— 当友元函数声明 (14.5.4)、显式实例化 (14.7.2) 或显式特化 (14.7.3) 指的是函数模板特化。
2 部分排序通过依次转换每个模板(参见下一段)并使用函数类型执行模板参数推导来选择两个函数模板中的哪一个比另一个更专业。推演过程确定模板中的一个是否比另一个更专业。如果是这样,更专业的模板是偏排序过程选择的模板。