码迷,mamicode.com
首页 > 编程语言 > 详细

Windows线程同步(未完)

时间:2016-01-12 21:28:13      阅读:304      评论:0      收藏:0      [点我收藏+]

标签:

先介绍一个创建线程的API,参考:https://msdn.microsoft.com/en-us/library/windows/desktop/ms682453%28v=vs.85%29.aspx

Creates a thread to execute within the virtual address space of the calling process.

HANDLE WINAPI CreateThread(
  _In_opt_  LPSECURITY_ATTRIBUTES  lpThreadAttributes,
  _In_      SIZE_T                 dwStackSize,
  _In_      LPTHREAD_START_ROUTINE lpStartAddress,
  _In_opt_  LPVOID                 lpParameter,
  _In_      DWORD                  dwCreationFlags,
  _Out_opt_ LPDWORD                lpThreadId
);

使用范例参考MSDN:https://msdn.microsoft.com/en-us/library/windows/desktop/ms682516%28v=vs.85%29.aspx

举例说明线程:

#include <iostream>
#include <windows.h>
using namespace std;

#define MAX_THREADS 20
#define BUF_SIZE 255

DWORD dwAccessOrder = 0;


DWORD WINAPI MyThreadFunction(LPVOID lpPara)
{
    DWORD *dwPara = (DWORD*)lpPara;
    cout << "这是第" << *dwPara << "个启动的线程!" << endl;
    return 0;
}


int main()
{
     DWORD   dwThreadIdArray[MAX_THREADS];
    HANDLE  hThreadArray[MAX_THREADS];
    LPVOID lpParam = nullptr;

    for (int i = 0; i < MAX_THREADS; i++)
    {
        lpParam = &i;
//可能有如下情况发生:参数还没有传递给线程,就已经把线程起起来了,比如i=12时,起起来了一个线程
        //线程还未接收到参数12时,就进入了下一次循环,i被覆盖,被赋值为了13,于是这时候又
        //起起来一个线程,可能就和刚刚的那个线程同时接到了参数13
        //而后接收到参数的线程,却又有可能比先接收到参数的线程输出到窗口
        hThreadArray[i] = CreateThread(
            NULL,                   
            0,                      
            MyThreadFunction,       
            lpParam,           
            0,                       
            &dwThreadIdArray[i]); 

    } 

    cout << "这里是主线程" << endl;
    for (int i = 0; i < MAX_THREADS; i++)
    {
        CloseHandle(hThreadArray[i]);

    }
    system("pause");
    return 0;
}

输出如图,毫无顺序性:

技术分享

由此我们可以判定,被创建出来的线程以及创建这些线程的主线程是独立的执行体。他们被“迅速”创建之后,就开始“独立行动”,去“争抢”CPU。其实,线程是由操作系统按照一定的调度算法来决定谁先谁后执行。多线程实际上是异步的,它的目的就是快速的、交替的获取CPU的执行权,让用户以为这些线程是并行执行的

我们对上边的例子稍作修改:

#include <iostream>
#include <windows.h>
using namespace std;

#define MAX_THREADS 20
#define BUF_SIZE 255

DWORD dwAccessOrder = 0;

DWORD WINAPI MyThreadFunction(LPVOID lpParam)
{
    dwAccessOrder++;
    cout << "这是第" << dwAccessOrder << "个启动的线程!" << endl;
    return 0;
}

int main()
{
     DWORD   dwThreadIdArray[MAX_THREADS];
    HANDLE  hThreadArray[MAX_THREADS];
    LPVOID lpParam = nullptr;

    for (int i = 0; i < MAX_THREADS; i++)
    {
        hThreadArray[i] = CreateThread(
            NULL,                   
            0,                      
            MyThreadFunction,       
            NULL,           
            0,                       
            &dwThreadIdArray[i]); 

    } 

    for (int i = 0; i < MAX_THREADS; i++)
    {
        CloseHandle(hThreadArray[i]);
    }
    system("pause");
    return 0;
}

输出如下结果:

技术分享

当线程t1和t2都需要访问变量dwAccessOrder时,如果t1正在修改dwAccessOrder的值但是尚未完成,此时操作系统把执行权切换到了t2,此时t2要读取dwAccessOrder就得到了一个错误的值。因此,我们必须使用某种手段使得需要被多个线程共享的数据在同一时刻只能被一个线程访问。这种手段,叫做线程同步

 

Windows线程同步(未完)

标签:

原文地址:http://www.cnblogs.com/predator-wang/p/5125590.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!