zoukankan      html  css  js  c++  java
  • 多线程编程(3) 从 CreateThread 说起[续]

    function CreateThread(
      lpThreadAttributes: Pointer;
      dwStackSize: DWORD;
      lpStartAddress: TFNThreadStartRoutine;
      lpParameter: Pointer;
      dwCreationFlags: DWORD; {启动选项}
      var lpThreadId: DWORD
    ): THandle; stdcall;
    

    CreateThread 的倒数第二个参数 dwCreationFlags(启动选项) 有两个可选值:
    0: 线程建立后立即执行入口函数;
    CREATE_SUSPENDED: 线程建立后会挂起等待.

    可用 ResumeThread 函数是恢复线程的运行; 可用 SuspendThread 再次挂起线程.
    这两个函数的参数都是线程句柄, 返回值是执行前的挂起计数.

    什么是挂起计数?
    SuspendThread 会给这个数 +1; ResumeThread 会给这个数 -1; 但这个数最小是 0.
    当这个数 = 0 时, 线程会运行; > 0 时会挂起.
    如果被 SuspendThread 多次, 同样需要 ResumeThread 多次才能恢复线程的运行.

    在下面的例子中, 有新线程不断给一个全局变量赋随机值;
    同时窗体上的 Timer 控件每隔 1/10 秒就把这个变量写在窗体标题;
    在这个过程中演示了 ResumeThread、SuspendThread 两个函数.

    运行效果图:



    代码文件:
    unit Unit1;
    
    interface
    
    uses
      Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
      Dialogs, StdCtrls, ExtCtrls;
    
    type
      TForm1 = class(TForm)
        Button1: TButton;
        Button2: TButton;
        Button3: TButton;
        Timer1: TTimer;
        procedure Button1Click(Sender: TObject);
        procedure Button2Click(Sender: TObject);
        procedure Button3Click(Sender: TObject);
        procedure FormCreate(Sender: TObject);
        procedure Timer1Timer(Sender: TObject);
      end;
    
    var
      Form1: TForm1;
    
    implementation
    
    {$R *.dfm}
    
    var
      hThread: THandle; {线程句柄}
      num: Integer;     {全局变量, 用于记录随机数}
    
    {线程入口函数}
    function MyThreadFun(p: Pointer): Integer; stdcall;
    begin
      while True do {假如线程不挂起, 这个循环将一直循环下去}
      begin
        num := Random(100);
      end;
      Result := 0;
    end;
    
    {建立并挂起线程}
    procedure TForm1.Button1Click(Sender: TObject);
    var
      ID: DWORD;
    begin
      hThread := CreateThread(nil, 0, @MyThreadFun, nil, CREATE_SUSPENDED, ID);
      Button1.Enabled := False;
    end;
    
    {唤醒并继续线程}
    procedure TForm1.Button2Click(Sender: TObject);
    begin
      ResumeThread(hThread);
    end;
    
    {挂起线程}
    procedure TForm1.Button3Click(Sender: TObject);
    begin
      SuspendThread(hThread);
    end;
    
    {下面是窗体代码}
    procedure TForm1.FormCreate(Sender: TObject);
    begin
      Timer1.Interval := 100;
    end;
    
    procedure TForm1.Timer1Timer(Sender: TObject);
    begin
      Text := IntToStr(num);
    end;
    
    end.
    

    窗体文件:
    object Form1: TForm1
      Left = 0
      Top = 0
      Caption = 'Form1'
      ClientHeight = 86
      ClientWidth = 269
      Color = clBtnFace
      Font.Charset = DEFAULT_CHARSET
      Font.Color = clWindowText
      Font.Height = -11
      Font.Name = 'Tahoma'
      Font.Style = []
      OldCreateOrder = False
      OnCreate = FormCreate
      PixelsPerInch = 96
      TextHeight = 13
      object Button1: TButton
        Left = 16
        Top = 24
        Width = 75
        Height = 25
        Caption = 'Button1'
        TabOrder = 0
        OnClick = Button1Click
      end
      object Button2: TButton
        Left = 97
        Top = 24
        Width = 75
        Height = 25
        Caption = 'Button2'
        TabOrder = 1
        OnClick = Button2Click
      end
      object Button3: TButton
        Left = 178
        Top = 24
        Width = 75
        Height = 25
        Caption = 'Button3'
        TabOrder = 2
        OnClick = Button3Click
      end
      object Timer1: TTimer
        OnTimer = Timer1Timer
      end
    end
    

    ResumeThread 和 SuspendThread 分别对应 TThread 的 Resume 和 Suspend 方法, 很好理解.

    接下来应该是 CreateThread 的第四个参数了.

  • 相关阅读:
    vue实践推荐
    angularjs实现checkbox的点击-全选功能-选中数据
    是你需要的前端编码风格吗?
    webpack--前端性能优化与Gzip原理
    基于verdaccio的npm私有仓库搭建
    使用uni-app开发微信小程序
    《JavaScript设计模式与开发实践》-- 迭代器模式
    《JavaScript设计模式与开发实践》-- 发布-订阅模式
    《JavaScript设计模式与开发实践》-- 策略模式
    《JavaScript设计模式与开发实践》-- 代理模式
  • 原文地址:https://www.cnblogs.com/del/p/1387638.html
Copyright © 2011-2022 走看看