AbuBakr
AbuBakr

Reputation: 998

boost::thread_group in C++11?

Is there anything like boost::thread_group in C++11?

I'm just trying to port my program from using boost:thread to C++11 threads and wasn't able to find anything equivalent.

Upvotes: 33

Views: 13576

Answers (3)

muxator
muxator

Reputation: 357

Beware: in @DailyLearner's solution the main flow of execution does not wait for the spawned threads. To show it, just print a message after the loop:

#include <iostream>
#include <thread>
#include <vector>

int main()
{
    constexpr int count = 3;
    std::vector<std::jthread> thread_group;

    for( int i = 1; i <= count; ++i )
    {
        thread_group.emplace_back([i=i](){
            std::this_thread::sleep_for(std::chrono::seconds(i));
            std::cout << " Thread " << i << " finished." << std::endl;
            });
    }
    // no need to join the threads here
    std::cout << "Finished" << std::endl;
}

Compile and run with g++ -std=c++20 thread.cpp && ./a.out.

Output:

Finished (WRONG)
 Thread 1 finished.
 Thread 2 finished.
 Thread 3 finished.

I've had success with @rustyx solution. Here's his version modified to show the different (and correct) behaviour:

#include <iostream>
#include <thread>
#include <vector>

void f(int i)
{
  std::this_thread::sleep_for(std::chrono::seconds(i));
  std::cout << " Thread " << i << " finished." << std::endl;
};

void join_all(std::vector<std::thread> &grp)
{
  for (auto &thread : grp)
    thread.join();
}

int main()
{
  std::vector<std::thread> grp;

  // to create threads
  grp.emplace_back([](){ f(3); });
  grp.emplace_back([](){ f(2); });
  grp.emplace_back([](){ f(1); });

  join_all(grp);

  std::cout << "Finished" << std::endl;
}

Output:

 Thread 1 finished.
 Thread 2 finished.
 Thread 3 finished.
Finished (OK)

Upvotes: 0

rustyx
rustyx

Reputation: 85531

thread_group didn't make it into C++11, C++14, C++17 or C++20 standards.

But a workaround is simple:

  std::vector<std::thread> grp;

  // to create threads
  grp.emplace_back(functor); // pass in the argument of std::thread()

  void join_all() {
    for (auto& thread : grp)
        thread.join();
  }

Not even worth wrapping in a class (but is certainly possible).

Upvotes: 11

Anthony Williams
Anthony Williams

Reputation: 68691

No, there's nothing directly equivalent to boost::thread_group in C++11. You could use a std::vector<std::thread> if all you want is a container. You can then use either the new for syntax or std::for_each to call join() on each element, or whatever.

Upvotes: 36

Related Questions