c ++中windows-thread的异常输出

时间:2016-04-25 17:47:45

标签: c++ multithreading winapi

我是c ++的新手并且尝试了一下。我开始使用CreateThread-Method创建一个线程。我还传入一个指向struct-method的指针,该方法引用了一个测试值。到现在为止还挺好。现在我在启动线程之前将值更改为0.当我启动程序时,evrything似乎像我预期的那样工作。但是当我在CreateThread-Method(到1)之后也改变了值时,线程总是输出1.我期望输出为0,因为我认为对变量的更改不会影响线程。或者至少输出0,然后是1。

现在我测试了一些东西: 如果我让主线程等待例如5000ms,那么线程的输出再次总是为0.但是没有它再次为1。

我希望你能帮助我理解这个问题。

以下是一些代码:

struct TESTSTRUCT{
  int test;
};

DWORD WINAPI testFunc(void* lpParam){

  TESTSTRUCT& params=*((TESTSTRUCT*)lpParam);

  int a=params.test;

  while(true){
      cout << a;
      Sleep(5000);
  }

  return 0;
}

int main(int argc, char *argv[]) {

  TESTSTRUCT teststr;
  teststr.test=0;
  HANDLE myhandle;
  myhandle = CreateThread(0, 0, testFunc, &teststr, 0, 0);

  Sleep(5000); // If left out, thread outputs always 1!

  teststr.test=1;

  cout << "main" << teststr.test;

  CloseHandle(myhandle);

  MSG msg;
  while(GetMessage(&msg, NULL, 0, 0))
  {
    TranslateMessage(&msg);
    DispatchMessage(&msg);
  }
}

1 个答案:

答案 0 :(得分:0)

见:

 myhandle = CreateThread(0, 0, testFunc, &teststr, 0, 0);

您将teststr引用通过testFunc。因此,您的main方法和testFunc操作相同的数据。改变一个会影响另一个。

要明确的是,它的工作方式是您获取teststr的地址,将其转换为void*,然后在testFunc内将其转回TESTSTRUCT& 1}}。这与您通过引用将teststr传递给testFunc的方式相同。

我想我应该提一下,没有锁定,无论睡眠时间是多少,你都会在线程的输出上出现竞争条件。让main睡眠时间足够长,一般情况下你会看到你的线程打印出“旧”值,但不能保证。