开发者

How to ease nested looping?

I find myself looping over vectors of vectors a lot:

std::vector<std::vector<int> > foo;

for(unsigned int i=0; i != foo.size(); ++i) {
 for(unsigned int j=0; j != foo[i].size(); ++j) {
  // use foo[i][j]
 }
}

I don't have a good minimal example why the "data" is represented best by a vector of vectors of int but let's don't doubt it here.

What do you suggest to simplify the looping? I could think of a function that implements the explicit looping and takes a pointer to a function for the body.

How to "generate" nested for-loops in case of more levels?

Are there languages that have "built-in" support for "nested looping"?

Than开发者_StackOverflow社区ks in advance,

Somebody


I could think of a function that implements the explicit looping and takes a pointer to a function for the body.

Seems like the visitor pattern:

http://en.wikipedia.org/wiki/Visitor_pattern

edit:

I have not tested the template part but something like this:

class Visitor
{
    public:
        template<typename T>
        void visit(const std::vector<T> &vector)
        {
            for(typename std::vector<T>::const_iterator it(vector.begin());
                it != vector.end();
                ++it)
            {
                visit(*it);
            }
        }

        void visit(int i)
        {
            // do something with i
        }
}


// usage:
std::vector<std::vector<int> > theData;

Visitor v;
v.visit(theData);
std::cout << v.result() << std::endl;


I think what you are looking for is Iterator pattern.

http://en.wikipedia.org/wiki/Iterator


There is no built-in looping for nested structures (given the depth of nesting could be arbitrary). You have several options.

Flatten the 2D vector into a single dimensional vector and iterate over that or, Use something like for_each, e.g.

template <typename T>
struct do_foo
{
  void operator()(T v)
  {
    // Use the v
  }
};

template <typename Handler, typename Container>
struct handle_nested
{
  void operator()(Container const& internal)
  {
    // inner loop, container type has been abstracted away and the handler type
    for_each(internal.begin(), internal.end(), Handler());
  }
};

// outer loop
for_each(foo.begin(), foo.end(), handle_nested<do_foo<int>, std::vector<int> >());


I think nested loops as the one you showed us aren't that bad. I would recommend to choose better names for the control variables. If there aren't better names maybe outerIndex and innerIndex can be used?! Also, sometimes moving the (complex) loop body into a function improves readability.


There's no 'built-in' support for vector looping, but if done right, a smart compiler may optimize your for loops into code, which may make use of advanced CPU features, which may improve performance.

Generally speaking, there's nothing wrong with nested loops. But more often than not, when you have a nested loop, that code may be optimized to run faster. But this depends heavily on the code inside the loop, i.e. on the thing you're trying to do with the data in the vectors.

As pointed out by others, using iterators would improve your code in terms of compliance with C++ best practices. It will not improve performance, but it will improve type safety and compiler may be able to point out to you about mistakes that neither you, nor compiler may not have noticed otherwise.

If the thing you're doing inside the loops is very simple -- say, incrementing a value if it satisfies a condition, then standard C++ algorithms, like std::for_each, and predicates may be used to make the code more concise and readable.

But don't get carried away by these things, keep it simple. ;)

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜