c++ - 重载模板函数时显式特化和常规函数之间的区别

标签 c++ templates overloading explicit-specialization

我今天很开心。这是第 7 题 n00b:

当您尝试重载模板函数时,显式特化和普通函数有什么区别?

什么情况下适合使用显式特化?我不太明白:

#include <iostream>

template <typename s> void test(s var1);
template <> void test<int>(int var1);

int main(){
    test(1);
    test(1.1);
    test("hello!!");
    return 0;
}

template <typename s> void test(s var1){
    std::cout << var1 << std::endl;
}

template <> void test<int>(int var1){
    std::cout << "int " << var1 << std::endl;
}

反对:

#include <iostream>

template <typename s> void test(s var1);
void test(int var1);

int main(){
    test(1);
    test(1.1);
    test("hello!!");
    return 0;
}

template <typename s> void test(s var1){
    std::cout << var1 << std::endl;
}

void test(int var1){
    std::cout << "int " << var1 << std::endl;
}

最佳答案

除了当编译器为函数调用寻找匹配的签名类型时,它会首先选择一个非模板之外,显式专门化的模板函数和非模板常规函数之间确实没有区别在尝试实例化可能满足所需签名匹配的任何可用模板函数之前,匹配所需签名的函数。

如果你要在头文件中声明和定义一个不是模板函数的函数,你必须将该函数声明为inline。这是因为模板函数在实际实例化之前不是与代码模块链接的实际函数。然后,链接器在编译代码模块后丢弃该实例化。如果链接器不这样做,那么每次 .cpp 文件包含头文件时,链接器都会提示函数的重复定义。在非模板函数上使用 inline 关键字在编译器级别具有类似的效果,因为只要在 .cpp 文件中使用该函数,编译器就会将该函数调用替换为头文件中 inline 函数的函数代码,并避免了函数调用的开销以及相关的堆栈事件记录设置和清理。因此,链接器不会提示函数的重复定义。

关于c++ - 重载模板函数时显式特化和常规函数之间的区别,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5986935/

相关文章:

c++ - 将 nullptr 传递给 std::string::assign 是否有效?

c++ - std::min_element 从类对象返回意外结果

C++ 计数图

c++ - OpenCV - 查找轮廓图像的高度和宽度

php - 将 __set 与数组一起使用已解决,但为什么呢?

c++ - 多态性和覆盖 C++ 类模板中的方法

c++ - 没有默认构造函数的重复元素模板化数组

c++ - 具有特定值的模板中的 "Pointless comparison"警告

c++ - 重载的缺点是什么?

c++ - 右值的函数重载