为成对容器的第一个元素提供迭代器

时间:2008-11-23 17:35:38

标签: c++ generics templates stl

我有一个装满对的容器。我想使用STL泛型算法迭代它(在我的情况下,它将是inner_product,但将其视为一般问题)。 我正在使用的算法首先要求使用迭代器。我可以首先提供特殊的迭代器,并且不会在对上迭代但是在每对的第一个元素上迭代吗?

我知道我可以手动完成,提供一个手工制作的函数对象,它将成为标准容器迭代器周围的包装器,将它引用到该对本身对的第一个成员,但我认为还有一个聪明的单行为我做。它会是什么?

4 个答案:

答案 0 :(得分:11)

我环顾四周,发现boost::transform_iterator。我想出了这个代码。令人惊讶的是它的工作原理:

#include <map>
#include <algorithm>
#include <iostream>
#include <string>
#include <iterator>
#include <boost/iterator/transform_iterator.hpp>
#include <boost/bind.hpp>
#include <boost/function.hpp>

int main() {
    typedef std::map<std::string, int>::value_type value_type;
    std::map<std::string, int> a;
    a["one"] = 1;
    a["two"] = 2;

    // returns the second element 
    boost::function<int(value_type&)> f = boost::bind(&value_type::second, _1);
    std::copy(boost::make_transform_iterator(a.begin(), f), 
              boost::make_transform_iterator(a.end(), f),
              std::ostream_iterator<int>(std::cout, " "));

}

它将"1 2 "打印到标准输出。

答案 1 :(得分:1)

您可以子类化,例如std :: vector :: const_iterator你自己,重新实现operator *和operator-&gt;返回该对中的第一个。您还需要创建自己的begin()和end()函数来返回自定义迭代器。

您还可以创建二进制函数类并将它们传递给inner_product。

答案 2 :(得分:1)

没有聪明的单线解决方案。你最好的希望是编写一个包装器迭代器。这实际上是一个非常规范的解决方案。您可以检查Boost是否已满足您的需求。如果没有,请尝试编写一个可以重用于其他问题的通用包装器。

STL包含一个名为reverse_iterator的迭代器包装器。这个名字意味着它的使用。

答案 3 :(得分:1)

最终,我认为你的想法是要走的路。您可以使用Boost来帮助您。首先,你需要一个带你的对的函数并返回第一个元素。我认为你可以使用Lambda library在线编写这样的函数,但为了便于阅读,我想我只是编写一个简单的函数来代替它。然后使用原始迭代器传递该函数,为序列的开始和结束构造transform_iterator