c++ - 函数模板专业化真的允许吗?
问题描述
根据这篇文章,它说(强调我的):
部分模板专业化允许我们专门化类(但不能专门化单个函数!)
似乎不允许函数部分模板专业化。这真的正确吗?
让我困惑的是,为什么这些代码片段可以编译成功:
//demo1.cpp
//first code snippet(https://coliru.stacked-crooked.com/a/0868610b5be94f2c)
//Why this function template specialization compiles?
//Because this is full template specialization other than partial template specialization?Am I right?
#include <iostream>
#include <string.h>
using namespace std;
template <class T>
void f(T)
{
T d;
std::cout <<"first one" << std::endl;
}
template <>
void f<int>(int)
{
int d;
std::cout <<"second one" << std::endl;
}
int main()
{
f(5.0);
f(1);
f('a');
}
另一个例子:
//demo2.cpp(https://coliru.stacked-crooked.com/a/7b1a94ad377ac1f6)
//Why this function template specialization compiles?
//I think it's function partial template specialization indeed.
#include <vector>
#include <iostream>
using namespace std;
//function template
template<typename T, class N> void compare(T num1, N num2) {
cout << "standard function template" << endl;
if(num1>num2)
cout << "num1:" << num1 << " > num2:" << num2 <<endl;
else
cout << "num1:" << num1 << " <= num2:" << num2 << endl;
}
//function partial template specialization
template<class N> void compare(int num1, N num2) {
cout<< "partitial specialization" <<endl;
if (num1>num2)
cout << "num1:" << num1 << " > num2:" << num2 << endl;
else
cout << "num1:" << num1 << " <= num2:" << num2 << endl;
}
int main() {
compare<int,int>(30,31);//call compare<int,int>(int num1, int num2)
compare(5,9); //call compare<int>(int num1, int num2)
compare(30,'1'); //call compare<char>(int num1, char num2)
}
为什么这个代码段无法编译,而前面的两个代码段编译成功?
#include <vector>
#include <iostream>
using namespace std;
template <class T1, class T2>
void f(){}
template <class T2>
void f<int, T2>(){} //It's function template sepcialization, isn't it? Why it could not be compiled?
int main() {}
以下是错误消息:
main.cpp:9:6: error: non-type partial specialization 'f<int, T2>' is not allowed 9 | void f<int, T2>(){} | ^~~~~~~~~~
已编辑:感谢 eerorika 的详细解释。
又提出一个问题,如何区分重载模板和部分特化函数模板?
换句话说,为什么 template<class N> void compare(int num1, N num2)
模板重载而 template <class T2> void f<int, T2>(){}
试图部分特化函数模板?
解决方案
函数模板专业化真的允许吗?
是的,但不是部分专业化。
似乎不允许函数部分模板特化。真的正确吗?
如果您的意思是部分专业化,那么函数模板确实不允许这样做。
// Why this fucntion template specialization compiles? // Because this is full template specialization ...?Am I right?
是的。
//Why this fucntion template specialization compiles? //I think it's function partcial template specialization
不,那根本不是模板专业化。那是一个单独的模板。这是一个超载。
为什么无法编译此代码段
因为它试图部分专门化一个函数模板。
如何区分重载模板和部分特化功能模板?
函数特化的语法是:
template<>
ReturnType template_name<template_argument_list>(parameter_list) {
// ^^^^^^^^^^^^^^^^^^^^^^^^
如果语法不是这样,那么它不是函数特化。请注意您的示例中缺少的突出显示的部分,它不是专业化的。如果该部分被遗漏,这将成为主要模板定义。
推荐阅读
- opencv - 如何在opencv中比较两个不同尺度的图像?
- javascript - 为什么这个 React 组件会渲染 4 次?
- html - 如何在markdown中编写给定的html?
- python - aiohttp/asyncio 无异常运行序列结果
- python - 根据相反的条件过滤熊猫数据框是否在列中为真/假
- deep-learning - 如何知道 id embedding 训练好还是坏
- python - 在两个用户的网页之间进行通信
- javascript - JS中如何拖拽图片
- postgresql - 在 VPC 中限制对 PostgreSQL 数据库的访问的最佳实践
- javascript - javascript中的嵌套子级