Lazarus中文社区

 找回密码
 立即注册(注册审核可向QQ群索取)

QQ登录

只需一步,快速开始

Lazarus IDE and 组件 下载地址版权申明
查看: 4346|回复: 2

Lazarus 多线程例子源码 Example DEMO

[复制链接]

该用户从未签到

发表于 2010-1-24 09:43:36 | 显示全部楼层 |阅读模式
  1. Type
  2.     TMyThread = class(TThread)
  3.     private
  4.       fStatusText : string;
  5.       procedure ShowStatus;
  6.     protected
  7.       procedure Execute; override;
  8.     public
  9.       Constructor Create(CreateSuspended : boolean);
  10.     end;
  11.   constructor TMyThread.Create(CreateSuspended : boolean);
  12.   begin
  13.     FreeOnTerminate := True;
  14.     inherited Create(CreateSuspended);
  15.   end;
  16.   procedure TMyThread.ShowStatus;
  17.   // this method is executed by the mainthread and can therefore access all GUI elements.
  18.   begin
  19.     Form1.Caption := fStatusText;
  20.   end;
  21.   procedure TMyThread.Execute;
  22.   var
  23.     newStatus : string;
  24.   begin
  25.     fStatusText := 'TMyThread Starting...';
  26.     Synchronize(@Showstatus);
  27.     fStatusText := 'TMyThread Running...';
  28.     while (not Terminated) and ([any condition required]) do
  29.       begin
  30.         ...
  31.         [here goes the code of the main thread loop]
  32.         ...
  33.         if NewStatus <> fStatusText then
  34.           begin
  35.             fStatusText := newStatus;
  36.             Synchronize(@Showstatus);
  37.           end;
  38.       end;
  39.   end;
  40. var
  41.     MyThread : TMyThread;
  42.   begin
  43.     MyThread := TMyThread.Create(True); // This way it doesn't start automatically
  44.     ...
  45.     [Here the code initialises anything required before the threads starts executing]
  46.     ...
  47.     MyThread.Resume;
  48.   end;
复制代码


如果您想使您的应用程序更加灵活,您可以创建一个线程的事件,这您的同步方法不会被紧紧与特定形式或类的耦合方式:您可以附加听众线程的事件。下面是一个例子:
  1.    Type
  2.     TShowStatusEvent = procedure(Status: String) of Object;
  3.     TMyThread = class(TThread)
  4.     private
  5.       fStatusText : string;
  6.       FOnShowStatus: TShowStatusEvent;
  7.       procedure ShowStatus;
  8.     protected
  9.       procedure Execute; override;
  10.     public
  11.       Constructor Create(CreateSuspended : boolean);
  12.       property OnShowStatus: TShowStatusEvent read FOnShowStatus write FOnShowStatus;
  13.     end;
  14.   constructor TMyThread.Create(CreateSuspended : boolean);
  15.   begin
  16.     FreeOnTerminate := True;
  17.     inherited Create(CreateSuspended);
  18.   end;
  19.   procedure TMyThread.ShowStatus;
  20.   // this method is executed by the mainthread and can therefore access all GUI elements.
  21.   begin
  22.     if Assigned(FOnShowStatus) then
  23.     begin
  24.       FOnShowStatus(fStatusText);
  25.     end;
  26.   end;
  27.   procedure TMyThread.Execute;
  28.   var
  29.     newStatus : string;
  30.   begin
  31.     fStatusText := 'TMyThread Starting...';
  32.     Synchronize(@Showstatus);
  33.     fStatusText := 'TMyThread Running...';
  34.     while (not Terminated) and ([any condition required]) do
  35.       begin
  36.         ...
  37.         [here goes the code of the main thread loop]
  38.         ...
  39.         if NewStatus <> fStatusText then
  40.           begin
  41.             fStatusText := newStatus;
  42.             Synchronize(@Showstatus);
  43.           end;
  44.       end;
  45.   end;
  46. Type
  47.     TForm1 = class(TForm)
  48.       Button1: TButton;
  49.       Label1: TLabel;
  50.       procedure FormCreate(Sender: TObject);
  51.       procedure FormDestroy(Sender: TObject);
  52.     private
  53.       { private declarations }
  54.       MyThread: TMyThread;
  55.       procedure ShowStatus(Status: string);
  56.     public
  57.       { public declarations }
  58.     end;
  59.   procedure TForm1.FormCreate(Sender: TObject);
  60.   begin
  61.     inherited;
  62.     MyThread := TMyThread.Create(true);
  63.     MyThread.OnShowStatus := @ShowStatus;
  64.   end;
  65.   procedure TForm1.FormDestroy(Sender: TObject);
  66.   begin
  67.     MyThread.Terminate;
  68.     MyThread.Free;
  69.     inherited;
  70.   end;
  71.   procedure TForm1.Button1Click(Sender: TObject);
  72.   begin
  73.    MyThread.Resume;
  74.   end;
  75.   procedure TForm1.ShowStatus(Status: string);
  76.   begin
  77.     Label1.Caption := Status;
  78.   end;
复制代码
回复

使用道具 举报

该用户从未签到

 楼主| 发表于 2010-1-24 09:45:05 | 显示全部楼层
有一个线程在Windows与潜在头痛,如果您使用-衣原体(堆栈检查)开关。原因不是很清楚堆栈检查将“触发任何TThread.Create如果您使用默认的堆栈大小”。唯一的工作暂时解决办法是根本不使用衣原体开关。请注意,不会导致在主线程例外,但在新创建的。
这个“看起来”像如果线程是从来就没有开始。
一个好的代码来检查这方面和其他例外,可以发生在线程创建是:
  1. MyThread:=TThread.Create(False);
  2.     if Assigned(MyThread.FatalException) then
  3.       raise MyThread.FatalException;
复制代码
此代码将确保任何例外,发生在线程创建将在您的主线程的问题。
回复 支持 反对

使用道具 举报

该用户从未签到

发表于 2010-1-26 14:43:29 | 显示全部楼层
我原先看一个类似手册的东西,上面是用BeginThread函数开启一个线程,总感觉不好用,还是lz这个比较爽一些...
回复 支持 反对

使用道具 举报

*滑块验证:

本版积分规则

QQ|手机版|小黑屋|Lazarus中国|Lazarus中文社区 ( 鄂ICP备16006501号-1 )

GMT+8, 2025-9-5 08:07 , Processed in 0.025770 second(s), 10 queries , Redis On.

Powered by Discuz! X3.4

Copyright © 2001-2021, Tencent Cloud.

快速回复 返回顶部 返回列表