Why may thread_local
not be applied to non-static data members? The accepted answer to this question says: "There is no point in making non-static structure or class members thread-local." Honestly, I see many good reasons to make non-static data members thread-local.
Assume we have some kind of ComputeEngine
with a member function computeSomething
that is called many times in succession. Some of the work inside the member function can be done in parallel. To do so, each thread needs some kind of ComputeHelper
that provides, for example, auxiliary data structures. So what we actually want is the following:
class ComputeEngine {
public:
int computeSomething(Args args) {
int sum = 0;
#pragma omp parallel for reduction(+:sum)
for (int i = 0; i < MAX; ++i) {
// ...
helper.xxx();
// ...
}
return sum;
}
private:
thread_local ComputeHelper helper;
};
Unfortunately, this code will not compile. What we could do instead is this:
class ComputeEngine {
public:
int computeSomething(Args args) {
int sum = 0;
#pragma omp parallel
{
ComputeHelper helper;
#pragma omp for reduction(+:sum)
for (int i = 0; i < MAX; ++i) {
// ...
helper.xxx();
// ...
}
}
return sum;
}
};
However, this will construct and destruct the ComputeHelper
between successive calls of computeSomething
. Assuming that constructing the ComputeHelper
is expensive (for example, due to the allocation und initialization of huge vectors), we may want to reuse the ComputeHelper
s between successive calls. This leads me to the following boilerplate approach:
class ComputeEngine {
struct ThreadLocalStorage {
ComputeHelper helper;
};
public:
int computeSomething(Args args) {
int sum = 0;
#pragma omp parallel
{
ComputeHelper &helper = tls[omp_get_thread_num()].helper;
#pragma omp for reduction(+:sum)
for (int i = 0; i < MAX; ++i) {
// ...
helper.xxx();
// ...
}
}
return sum;
}
private:
std::vector<ThreadLocalStorage> tls;
};
- Why may
thread_local
not be applied to non-static data members? What is the rationale behind this restriction? Have I not given a good example where thread-local non-static data members make perfect sense? - What are best practices to implement thread-local non-static data members?
Aucun commentaire:
Enregistrer un commentaire