使用迭代器实现STL vector的构造函数

5

我正在尝试用C++98实现std::vector。

我参考了https://www.cplusplus.com/reference/vector/vector/vector/

所以,在构造函数中,我按照以下方式编写了vector。

explicit vector (size_type n, const value_type& val = value_type(),
                 const allocator_type& alloc = allocator_type())
{
...
}

template <class InputIterator>
         vector (InputIterator first, InputIterator last,
                 const allocator_type& alloc = allocator_type())
{
...
}

然而,当我在主函数中测试该向量时,它并没有按照我所期望的工作。

int main(void)
{
    vector<int> vec(3, 100);
}

我想调用 explicit vector (size_type n, const value_type& val = value_type(), const allocator_type& alloc = allocator_type()),但却调用了带有迭代器的构造函数。

所以,我的问题是:

  1. 为什么调用了带有迭代器的构造函数?
    这是因为“explicit”吗?

  2. 在主程序中应该使用 'size_t' 来调用带有 'val' 的构造函数吗?
    还是有一种方法可以检查迭代器?

很抱歉打扰您,但我真的不知道为什么会发生这种情况...


cppreference的页面上提到了一些更多的细节。具体来说,“仅当InputIt满足LegacyInputIterator时,此重载才参与重载决议,以避免与重载(3)产生歧义。”我不知道用于产生此效果的机制是什么。 - Nathan Pierson
1个回答

1

实现通常会使用某种类型特征来启用/禁用迭代器版本,具体取决于迭代器类型是否真正是迭代器。

例如,它的概念可能是这样的:

template <class InputIterator, typename = enable_if_t<IsIterator_v<InputIterator>>
vector(InputIterator first, InputIteratorLast)

(或者更正确地避免仅在默认模板参数上有区别的模板重新定义,如在注释和这个notes中所述:):

// this is more the way it's actually practically implemented
template <class InputIterator, enable_if_t<IsIterator_v<InputIterator>, int> = 0>
    vector(InputIterator first, InputIteratorLast)

IsIterator_v是实现定义的类型特征,用于测试迭代器要求。

因此,在您的构造函数示例vector(3, 100)中,迭代器构造函数版本将不参与重载决议。

在C++98中,enable_if不存在,但实现仍会使用类似的概念检查。


你的 enable_if 有 bug,你需要使用 enable_if_t<..., int> = 0。请参考 https://en.cppreference.com/w/cpp/types/enable_if#Notes。 - Passer By
是的,但这更像是一种实现细节。主要点是使用类型特征来启用/禁用重载。已更新。谢谢。 - StPiere

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接