我有一个c++类Finder
,它在容器中存储位置和一些额外的数据。这种容器有std::string
型,也有char *
型或MyString
型。例如,该类看起来像这样(Iterator<TContainer>::Type
是一个trait/元函数,它返回给定容器的迭代器类型):
template <typename TContainer>
class Finder
{
public:
typedef typename Iterator<TContainer>::Type TIterator;
TIterator iterator;
// Initialization of iterator: How to do it generically?
// Finder {} // problem with pointers!
// Finder() : iterator(0) {} // problem with iterators!
};
现在的主要问题是如何初始化可以是指针或迭代器的迭代器。如果我只想支持我自己的容器,那么我可以简单地实现一个构造函数,它接受nullptr_t
,遵循nullptr习惯用法。但是,由于我想支持指针、我自己的迭代器和 STL迭代器,所以这里有点超出了深度。
我能想到的最好的事情是写一个getNil<>()
函数,例如下面的代码。然而,现在至少出现了三个问题:
这是实现我的目标的最好方法吗?
如何确定类型是否为STL迭代器?我可能需要一些
#if
s,并为每个编译器/STL版本定制代码来使用。是否有可能在STL中获得nil迭代器?
x-y
的结果在std::vector<int> x, y; int x = x-y;
定义吗?
代码:
// Forward declaration.
template <typename T>
T getNil<T>();
template <typename TValue> TValue * getNil<TValue *>()
{ return NULL; }
template <typename TValue> TValue * const getNil<TValue * const>()
{ return NULL; }
template <> TValue * const getNil<MyIterator>()
{ return MyIterator(nullptr); } // nullptr from above idiom
template <> TStlIterator
boost::enable_if<
MagicallyDetermineIfIsStlIterator<TStlIterator>::value,
TStlIterator>
getNil<TStlIterator>()
{ return MyIterator(nullptr); } // nullptr from above idiom
Finder() : iterator() { }
应该可以。未在初始化列表中为成员提供参数将调用具有默认构造函数的类型的默认构造函数,并将零初始化包含指针的POD类型(如果类型没有默认构造函数,则将失败,但在您的场景中似乎不太可能)。