I have defined a class that has std::mutex my_mutex
as its private member variable. But when I try to use it using lock_guard
in a member function which is called from different threads, the compiler throws up a lots of errors. If I keep this mutex outside the class it works. The code is as follows
class ThreadClass
{
std::mutex my_mutex;
public:
void addToList(int max, int interval)
{
std::lock_guard<std::mutex> guard(my_mutex);
for (int i = 0; i < max; i++)
{
// Some operation
}
}
};
int main()
{
std::thread ct(&ThreadClass::addToList,ThreadClass(),100,1);
std::thread ct2(&ThreadClass::addToList,ThreadClass(),100,10);
std::thread ct3(&ThreadClass::print,ThreadClass());
ct.join();
ct2.join();
ct3.join();
}
If the same my_mutex
is kept out of the class then it works fine. So when the same variable is within the class and called within the member function acted on by a thread, does it treat like a static member?
The std::thread
constructor copies the arguments that are passed to the executed function. But std::mutex
is non-copyable and so ThreadClass
is non-copyable if it has such a member.
You are passing a temporary ThreadClass
object to std::thread
, but you probably want to use the same object in all your threads. You can use std::ref
to pass a reference of an existing object. The following code compiles on GCC 7.1.0:
#include <thread>
#include <mutex>
class ThreadClass
{
std::mutex my_mutex;
public:
void addToList(int max, int interval)
{
std::lock_guard<std::mutex> guard(my_mutex);
// ...
}
void print()
{
// ...
}
};
int main()
{
ThreadClass obj;
std::thread ct(&ThreadClass::addToList, std::ref(obj), 100, 1);
std::thread ct2(&ThreadClass::addToList, std::ref(obj), 100, 10);
std::thread ct3(&ThreadClass::print, std::ref(obj));
ct.join();
ct2.join();
ct3.join();
}
Passing a pointer to the object instead of a reference should also work:
std::thread ct(&ThreadClass::addToList, &obj, 100, 1);