标题不是最好的,所以让我解释一下:我正在试验自定义 mini-STL(用于学习目的)并且目前正在实现 std::distance
函数。对于随机访问迭代器和简单输入迭代器,该函数的行为必须不同。
函数重载
std(在微软的实现中)和 EASTL 都使用运算符重载来选择合适的函数,像这样:
namespace internal
{
template <typename Iter>
inline typename IteratorTraits<Iter>::DifferenceType DistanceImpl(Iter first, Iter last, InputIteratorTag)
{
// ...
}
template <typename Iter>
inline typename IteratorTraits<Iter>::DifferenceType DistanceImpl(Iter first, Iter last, RandomAccessIteratorTag)
{
// ...
}
}
template <typename Iter>
inline typename IteratorTraits<Iter>::DifferenceType Distance(Iter first, Iter last)
{
// the last parameter of the function selects the proper DistanceImpl
return internal::DistanceImpl<Iter>(first, last, (typename IteratorTraits<Iter>::IteratorCategory)());
}
我猜临时对象(类别标签参数是一个空结构)将被优化掉,因为它没有被使用。
具有静态函数的类特化
带有静态函数的辅助类的特化是什么?
namespace internal
{
template <typename Cat>
struct DistanceImpl;
template <>
struct DistanceImpl<InputIteratorTag>
{
template <typename Iter>
inline static typename IteratorTraits<Iter>::DifferenceType Calc(Iter first, Iter last)
{
// ...
}
};
template <>
struct DistanceImpl<RandomAccessIteratorTag>
{
template <typename Iter>
inline static typename IteratorTraits<Iter>::DifferenceType Calc(Iter first, Iter last)
{
// ...
}
};
}
template <typename Iter>
inline typename IteratorTraits<Iter>::DifferenceType Distance(Iter first, Iter last)
{
return internal::DistanceImpl<typename IteratorTraits<Iter>::IteratorCategory>::Calc<Iter>(first, last);
}
问题
- 两种解决方案之间的差异? (包括性能和可靠性)
- 优点/缺点?
最佳答案
标签分发自动处理继承层次结构;明确的特化没有。这对于迭代器尤其重要,因为标准迭代器类别标签形成了继承层次结构:random_access_iterator_tag
派生自 bidirectional_iterator_tag
派生自input_iterator_tag
。
当通过选择输入迭代器重载给定前向或双向迭代器时,第一个版本开箱即用。第二个不需要并且需要额外的特化或其他一些更改。
关于c++ - 模板类特化与函数重载,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41427954/