0

In my code I want to create a bunch of objects of a class and then give each object a separate thread so objects can all carry out actions at the same time as each other.

for (i = 0; i < ROBOTCOUNT; i++)
{
    Robot* r = new Robot;
    boost::thread t(r);
    robotList.push_back(r);
}

I want to do something like the code above. The code doesn't compile if it's like that, but that is the general idea of what I want. Does anyone know how to do what I want?

Thanks

Jigglypuff
  • 1,433
  • 6
  • 24
  • 38
  • @KerrekSB It's the class that I'm creating objects of. – Jigglypuff Aug 23 '12 at 01:22
  • No kidding, but how is it *defined*?! – Kerrek SB Aug 23 '12 at 01:24
  • You really shouldn't do things this way. Forcing a static mapping between threads and types of work you need to do is usually extremely inefficient. It's like a fast food restaurant that has one employee for each register, one for each station, one for each table that might need to be wiped, and so on. It makes more sense to have a fixed pool of employees and assign them jobs based on present need. – David Schwartz Aug 23 '12 at 01:25
  • @KerrekSB Sorry I'm not sure I entirely get what you mean. It's got a constructor that takes no parameters. – Jigglypuff Aug 23 '12 at 01:26

1 Answers1

3

The following code should work in C++11 and executes multiple Worker::foo()s in parallel:

#include <thread>
#include <memory>
#include <vector>

struct Worker
{
    void foo();
};

int main()
{
    std::vector<std::unique_ptr<Worker>> workers;
    std::vector<std::thread>             threads;

    workers.reserve(N);
    threads.reserve(N);

    for (unsigned int i = 0; i != N; ++i)
    {
        workers.emplace_back(new Worker);
        threads.emplace_back(&Worker::foo, workers.back().get());
    }

    // ... later ...

    for (auto & t : threads) { t.join(); }
}

You could even do without the unique pointers if you trust your element references to remain valid:

std::deque<Worker> workers;

// ...

for (unsigned int i = 0; i != N; ++i)
{
    workers.emplace_back(); // pray this doesn't invalidate
    threads.emplace_back(&Worker::foo, std::ref(workers.back()));
}
Kerrek SB
  • 464,522
  • 92
  • 875
  • 1,084
  • No need to pray if you reserved up front. :) – GManNickG Aug 23 '12 at 01:47
  • 1
    @GManNickG: I know... but it still made me feel queasy -- you just know that someone is going to come and add workers dynamically, and then there's no upper bound. Anyway, I fixed it! – Kerrek SB Aug 23 '12 at 07:56