Die Standard-Antworten darauf lauten:
- Kopf in den Sand stecken und die Problematik ignorieren. (So nicht! So ganz sicherlich nicht!)
- Sich nen std::lock_guard zu schnappen und sich die Thread-Safety selber basteln.
D.h. mit C++11 sollte es keine Probleme mehr geben. Sollte.Sektion 6.7 Abs. 4 von http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2012/n3337.pdf hat geschrieben:If control enters the declaration concurrently while the variable is being initialized, the concurrent execution shall wait for completion of the initialization.
Visual C++ 2010 implemententiert das schon einmal nicht. Mit Visual C++ 2012 (Vanilla) geht das auch nicht und mit dem November CTP auch nicht. Code:
Code: Alles auswählen
// Für /Wall
#pragma warning(disable : 4350 4514 4571 4625 4626 4710 4711 4820)
#include <future>
#include <iostream>
int calculate(int a, int b)
{
static int result = 2*a + b;
return result;
}
int main(int argc, char * argv[])
{
int a, b;
std::cin >> a >> b;
std::future<int> r1 = std::async(calculate, a, b);
std::future<int> r2 = std::async(calculate, a, b);
std::cout << r1.get() << " " << r2.get();
return 0;
}
Code: Alles auswählen
int calculate(int a, int b)
{
00C71ED0 push ebp
00C71ED1 mov ebp,esp
static int result = 2*a + b;
00C71ED3 mov eax,dword ptr ds:[00C79E60h]
00C71ED8 test al,1
00C71EDA jne calculate+24h (0C71EF4h)
00C71EDC mov ecx,dword ptr [ b]
00C71EDF or eax,1
00C71EE2 mov dword ptr ds:[00C79E60h],eax
00C71EE7 mov eax,dword ptr [a]
00C71EEA lea eax,[ecx+eax*2]
00C71EED mov dword ptr ds:[00C79E58h],eax
}
00C71EF2 pop ebp
00C71EF3 ret
return result;
00C71EF4 mov eax,dword ptr ds:[00C79E58h]
}
00C71EF9 pop ebp
00C71EFA ret
1>C:\Program Files (x86)\Microsoft Visual Studio 11.0\VC\include\thr/xthread(172): warning C4265: 'std::_Pad' : class has virtual functions, but destructor is not virtual
1> instances of this class may not be destructed correctly
1>main.cpp(10): warning C4640: 'result' : construction of local static object is not thread-safe
1>main.cpp(15): warning C4100: 'argv' : unreferenced formal parameter
1>main.cpp(15): warning C4100: 'argc' : unreferenced formal parameter
Ich hoffe, dass ich jetzt keinen Mist gebaut habe. Was sagt ihr dazu?