简体   繁体   English

在VS2015中C ++本地静态变量初始化是否是线程安全的

[英]Is C++ local static variable initialization thread-safe in VS2015

According to https://msdn.microsoft.com/en-us/library/hh567368.aspx 根据https://msdn.microsoft.com/en-us/library/hh567368.aspx

Magic statics ( http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2008/n2660.htm ) are supported on VS2015 VS2015支持Magic statics( http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2008/n2660.htm

However testing the following code in debug x64 Vs2015 Update 3 但是,在调试x64 Vs2015 Update 3中测试以下代码

#include "stdafx.h"
#include <iostream>
#include <windows.h>
#include <tchar.h>

#define MAX_THREADS 5

class Sleeper
{
public:
    Sleeper()
    {
        std::cout << "Sleeper \n";
        Sleep(100000);
    }
};

DWORD WINAPI MyThreadFunction(LPVOID lpParam)
{
    std::cout << "Sleeper Start" << (int)lpParam << "\n";
    static Sleeper s;
    std::cout << "Sleeper Done" << (int)lpParam << "\n";
    return 0;
}

int main(int, char**)
{
    DWORD   dwThreadIdArray[MAX_THREADS];
    HANDLE  hThreadArray[MAX_THREADS];

    // Create MAX_THREADS worker threads.

    for (int i = 0; i<MAX_THREADS; i++)
    {
        // Create the thread to begin execution on its own.
        hThreadArray[i] = CreateThread(
            NULL,                   // default security attributes
            0,                      // use default stack size  
            MyThreadFunction,      // thread function name
            (LPVOID)i,               // argument to thread function 
            0,                     // use default creation flags 
            &dwThreadIdArray[i]);   // returns the thread identifier 

                                    // Check the return value for success.
                                    // If CreateThread fails, terminate execution. 
                                    // This will automatically clean up threads and memory. 
        if (hThreadArray[i] == NULL)
        {
            ExitProcess(3);
        }
    } // End of main thread creation loop.

      // Wait until all threads have terminated.
    WaitForMultipleObjects(MAX_THREADS, hThreadArray, TRUE, INFINITE);

    // Close all thread handles and free memory allocations.
    for (int i = 0; i<MAX_THREADS; i++)
    {
        CloseHandle(hThreadArray[i]);
    }

    return 0;
}

gives output 给出输出

Sleeper Start0 Sleeper Sleeper Start2 Sleeper Start3 Sleeper Start1 Sleeper Start4 Sleeper Start0 Sleeper Sleeper Start2 Sleeper Start3 Sleeper Start1 Sleeper Start4

Which indicates that initializing static variable s is actually not thread safe. 这表明初始化静态变量s实际上不是线程安全的。

Yes it does. 是的,它确实。 The test was wrong. 测试错了。 Removing the word sleeper from MyThreadFunction shows the expected output 从MyThreadFunction中删除单词sleeper会显示预期的输出

Start1 Sleeper Start4 Start3 Start0 Start2 Done3 Done1 Done0 Done2 Done4 Start1 Sleeper Start4 Start3 Start0 Start2 Done3 Done1 Done0 Done2 Done4

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM