模板功能:混合逐个复制传递和按引用传递
Template functions : mixing pass-by-copy & pass-by-reference
我有一个模板函数,负责将模板值写入流。它看起来像这样:
template < typename T >
void Write( T value, std::ostream& stream, endianness_t endian );
我已经实现了基本类型的版本:int、uint、float等。现在,如果我想写一个更复杂的结构,比如一个std::字符串,我这样声明:
template<>
inline void Write( const std::string& value, std::ostream& stream, endianness_t endian ) { // Notice the reference
...
}
我不能在不显式调用"引用传递"版本的情况下调用它:
Write( strValue, stream, LITTLE_ENDIAN ); // error : tries to call Write<std::string>, undefined
Write< const std::string& >( strValue, stream, LITTLE_ENDIAN ); // OK, Write<const std::string&> is properly defined
问题是,对于我想做的事情来说,它太冗长了
我的问题是:我如何让编译器猜测我想要使用的版本是"通过引用"的版本?
我是否必须更改模板函数以获取常量引用?如果是的话,我可以专门化是否对基元类型使用"传递副本"吗?
比起模板专业化,您应该更喜欢重载,这样做可以解决您的问题,我认为:
inline void Write( const std::string& value, std::ostream& stream, endianness_t endian ) {
// ...
}
我还建议您回过头来,将您提到的int
等所有专业化改为重载。
不要为您想要使用的每种可能的类型提供重载。这首先打破了使用泛型代码的逻辑。话虽如此,为每种类型提供专业化的需求可能会指出,这并不是模板最成功的应用,更不用说像Sutter所说的那样,扰乱功能模板专业化并不是最漂亮的选择
由于您需要在互斥类型(内置和非内置)之间进行逻辑分离,因此有一个替代方案:
template<class T>
typename std::enable_if< std::is_fundamental<T>::value >::type foo_func(T arg)
{
std::cout << "Call for built in types" << std::endl;
}
template<class T>
typename std::enable_if< !std::is_fundamental<T>::value >::type foo_func(T const &arg)
{
std::cout << "Call for non built in types" << std::endl;
}
在这里解释代码发生了什么:
1) std::is_fundmental在编译时将分别返回false或true,具体取决于T是用户定义类型还是内置类型。
2) std::enable_if将"允许"在第一种情况下为true声明函数模板,在第二种情况下声明false,因此不会出现解决问题。
3) 因此,当为内置类型调用foo_func时,将使用第一个版本,并按值传递T(int、float等)(这对内置类型来说更快)。。。你可以想象在另一种情况下会发生什么。
您可以更改通用模板以传递const-ref:
template < typename T >
void Write( const T& value, std::ostream& stream, endianness_t endian );
相关文章:
- 按值传递变量与按引用传递变量具有相同的结果
- 获取 std::函数以推断按引用传递/按值传递
- C++/11 auto 关键字是在更有效时推导参数进行按引用传递,还是始终按值传递?
- 使用 enable_if 在按值传递与按引用传递之间更改函数声明
- 按引用传递和按地址传递之间的差异
- C++按引用传递还是按值传递?
- 可移动但不可复制的对象:按值传递还是按引用传递?
- 使用增量运算符按引用传递
- C++函数,按引用传递
- 按引用传递和动态内存分配之间的区别是什么
- 通过查看程序集来比较按值传递与按引用传递性能
- 在形式参数列表中自动使用 const 和按引用传递的任何明显后果
- C++复制按引用返回和按常量引用值返回
- 按引用传递函数参数
- c++避免复制通过引用传递给函数的参数
- C++按引用传递:如何使用调用堆栈
- 为什么按值传递 int 比按引用传递更快
- 是使用按引用传递来填充容器更好,还是使用返回值来填充容器更好
- 模板功能:混合逐个复制传递和按引用传递
- 是按值传递然后移动构造更好,还是按引用传递然后复制构造更好