【问题标题】:Function using iterators to perform a object operation使用迭代器执行对象操作的函数
【发布时间】:2017-05-28 20:17:53
【问题描述】:

假设我有一个 std::array<SomeType, N>,我想调用一个函数,该函数使用迭代器来处理 std::array 中的对象,但不知道容器是 std::array

SomeType 是一个具有公共成员函数 doSomething() 的类

例如一个函数可能是:

template<typename Iterator>
void action(Iterator &beg, Iterator &end) {
  for (; beg != end; ++beg)
    beg->doSomething();
}

可以通过以下方式调用此函数:

int main() {
  std::array<SomeType, 10> a;

  action<std::array<SomeType, 10>::iterator>(a.begin(), a.end());
}

但我想知道这是否是这样做的方法?特别是因为模板可以用于每个类。有没有办法将函数限制为SomeType,而不让函数知道容器是std::array

【问题讨论】:

  • 编写的代码无法编译。至少它不是格式良好的 C++。 Demo

标签: c++ c++11 templates iterator containers


【解决方案1】:
  1. 修复你的代码:你不应该需要左值参数。事实上,迭代器旨在高效地复制。

    template<typename Iterator>
    void action(Iterator beg, Iterator end)
    //          ^^^^^^^^^^^^  ^^^^^^^^^^^^
    
  2. 让模板参数推导完成它的工作:

    action(a.begin(), a.end());
    

【讨论】:

    【解决方案2】:

    请注意,标准库已经有许多算法涵盖了“在某个容器中的某个范围内做同样的事情”的一般情况:

    #include <array>
    #include <vector>
    #include <algorithm>
    #include <numeric>
    #include <iterator>
    
    struct SomeType
    {
      void doSomething();
    
      SomeType mutatedCopy() const;
    
      int someValue() const;
    };
    
    int add_value(int i, const SomeType& st) {
      return i + st.someValue();
    }
    
    void call_something(SomeType& st) { st.doSomething(); }
    auto mutate_copy(SomeType const& st) { return st.mutatedCopy(); }
    
    int main() {
      std::array<SomeType, 10> a;
      std::vector<SomeType> b;
    
      std::for_each(a.begin(), a.end(), call_something);
      std::for_each(b.begin(), b.end(), call_something);
    
      std::transform(a.begin(), a.end(), a.begin(), mutate_copy);
      std::transform(b.begin(), b.end(), b.begin(), mutate_copy);
    
      auto tot = std::accumulate(a.begin(), a.end(), 0, add_value)
               + std::accumulate(b.begin(), b.end(), 0, add_value);
    
      // you can even transform into dissimilar containers:
    
      std::transform(a.begin(), a.end(), std::back_inserter(b), mutate_copy);
    
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2020-02-03
      • 1970-01-01
      • 2014-08-29
      • 2018-12-10
      • 2023-03-20
      • 2014-03-11
      • 1970-01-01
      • 2012-04-27
      相关资源
      最近更新 更多