多线程临界区问题。全部分数了。谢谢! ( 积分: 26 )

  • 主题发起人 主题发起人 subcom
  • 开始时间 开始时间
S

subcom

Unregistered / Unconfirmed
GUEST, unregistred user!
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls;
type
Tbuffer = record
SrsNo:String;
Srscont:string;
Rcvtime:Tdatetime;
tag:integer;
end;
TForm1 = class(TForm)
Button1: TButton;
Edit1: TEdit;
Edit2: TEdit;
procedure Button1Click(Sender: TObject);
private
{ Private declarations }
ReadPos,WritePos:integer;
TempBuffer : array [0..255] of Tbuffer;
function MyThreadFunc(P:pointer):Longint;stdcall;
function MyThreadFunc1(P:pointer):Longint;stdcall;

public
InterlockedCrit : TRTLCriticalSection;
{ Public declarations }
end;

var
Form1: TForm1;
implementation
{$R *.dfm}
function Tform1.MyThreadFunc(P:pointer):Longint;stdcall;
var i:integer;
DC:HDC;S:string;
begin
DC:=GetDC(Form1.Handle);
while not application.Terminateddo
begin
EnterCriticalSection( InterlockedCrit );
if WritePos =256 then
WritePos := 0;
TempBuffer[WritePos].SrsNo := inttostr(i);
TempBuffer[WritePos].Srscont := inttostr(i);
TempBuffer[WritePos].Rcvtime := now;
edit1.Text := inttostr(i);
inc(WritePos);
inc(i);
LeaveCriticalSection( InterlockedCrit );
end;
end;

function Tform1.MyThreadFunc1(P:pointer):Longint;stdcall;
var i:integer;
DC:HDC;S:string;
begin
DC:=GetDC(Form1.Handle);
while not application.Terminateddo
begin
EnterCriticalSection( InterlockedCrit );
if ReadPos =256 then
ReadPos := 0;
TempBuffer[ReadPos].SrsNo := inttostr(i);
TempBuffer[ReadPos].Srscont := inttostr(i);
TempBuffer[ReadPos].Rcvtime := now;
edit2.Text := inttostr(i);
inc(ReadPos);
inc(i);
LeaveCriticalSection( InterlockedCrit );
end;
end;

procedure TForm1.Button1Click(Sender: TObject);
var hThread:Thandle;//定义一个句柄
ThreadID:DWord;
begin
//创建线程,同时线程函数被调用
hthread:=CreateThread(nil,0,@Tform1.MyThreadfunc,nil,0,ThreadID);
hthread:=CreateThread(nil,0,@Tform1.MyThreadfunc1,nil,0,ThreadID);
end;

end.
 
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls;
type
Tbuffer = record
SrsNo:String;
Srscont:string;
Rcvtime:Tdatetime;
tag:integer;
end;
TForm1 = class(TForm)
Button1: TButton;
Edit1: TEdit;
Edit2: TEdit;
procedure Button1Click(Sender: TObject);
private
{ Private declarations }
ReadPos,WritePos:integer;
TempBuffer : array [0..255] of Tbuffer;
function MyThreadFunc(P:pointer):Longint;stdcall;
function MyThreadFunc1(P:pointer):Longint;stdcall;

public
InterlockedCrit : TRTLCriticalSection;
{ Public declarations }
end;

var
Form1: TForm1;
implementation
{$R *.dfm}
function Tform1.MyThreadFunc(P:pointer):Longint;stdcall;
var i:integer;
DC:HDC;S:string;
begin
DC:=GetDC(Form1.Handle);
while not application.Terminateddo
begin
EnterCriticalSection( InterlockedCrit );
if WritePos =256 then
WritePos := 0;
TempBuffer[WritePos].SrsNo := inttostr(i);
TempBuffer[WritePos].Srscont := inttostr(i);
TempBuffer[WritePos].Rcvtime := now;
edit1.Text := inttostr(i);
inc(WritePos);
inc(i);
LeaveCriticalSection( InterlockedCrit );
end;
end;

function Tform1.MyThreadFunc1(P:pointer):Longint;stdcall;
var i:integer;
DC:HDC;S:string;
begin
DC:=GetDC(Form1.Handle);
while not application.Terminateddo
begin
EnterCriticalSection( InterlockedCrit );
if ReadPos =256 then
ReadPos := 0;
TempBuffer[ReadPos].SrsNo := inttostr(i);
TempBuffer[ReadPos].Srscont := inttostr(i);
TempBuffer[ReadPos].Rcvtime := now;
edit2.Text := inttostr(i);
inc(ReadPos);
inc(i);
LeaveCriticalSection( InterlockedCrit );
end;
end;

procedure TForm1.Button1Click(Sender: TObject);
var hThread:Thandle;//定义一个句柄
ThreadID:DWord;
begin
//创建线程,同时线程函数被调用
hthread:=CreateThread(nil,0,@Tform1.MyThreadfunc,nil,0,ThreadID);
hthread:=CreateThread(nil,0,@Tform1.MyThreadfunc1,nil,0,ThreadID);
end;

end.
 
为什么我的线程一进入临界区就出现错误?
 
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls;
type
Tbuffer = record
SrsNo:String;
Srscont:string;
Rcvtime:Tdatetime;
tag:integer;
end;
TForm1 = class(TForm)
Button1: TButton;
Edit1: TEdit;
Edit2: TEdit;
procedure Button1Click(Sender: TObject);
private
{ Private declarations }
ReadPos,WritePos:integer;
TempBuffer : array [0..255] of Tbuffer;
function MyThreadFunc(P:pointer):Longint;stdcall;
function MyThreadFunc1(P:pointer):Longint;stdcall;

public
InterlockedCrit : TRTLCriticalSection;
{ Public declarations }
end;

var
Form1: TForm1;
implementation
{$R *.dfm}
function Tform1.MyThreadFunc(P:pointer):Longint;stdcall;
var i:integer;
DC:HDC;S:string;
begin
DC:=GetDC(Form1.Handle);
while not application.Terminateddo
begin
with Form1do
begin
EnterCriticalSection( InterlockedCrit );
if WritePos =256 then
WritePos := 0;
TempBuffer[WritePos].SrsNo := inttostr(i);
TempBuffer[WritePos].Srscont := inttostr(i);
TempBuffer[WritePos].Rcvtime := now;
edit1.Text := inttostr(i);
inc(WritePos);
inc(i);
LeaveCriticalSection( InterlockedCrit );
end;
end;
end;

function Tform1.MyThreadFunc1(P:pointer):Longint;stdcall;
var i:integer;
DC:HDC;S:string;
begin
DC:=GetDC(Form1.Handle);
while not application.Terminateddo
begin
with Form1do
begin
EnterCriticalSection( InterlockedCrit );
if Form1.ReadPos =256 then
ReadPos := 0;
TempBuffer[ReadPos].SrsNo := inttostr(i);
TempBuffer[ReadPos].Srscont := inttostr(i);
TempBuffer[ReadPos].Rcvtime := now;
edit2.Text := inttostr(i);
inc(ReadPos);
inc(i);
LeaveCriticalSection( InterlockedCrit );
end;
end;
end;

procedure TForm1.Button1Click(Sender: TObject);
var hThread:Thandle;//定义一个句柄
ThreadID:DWord;
begin
//创建线程,同时线程函数被调用
InitializeCriticalSection(InterlockedCrit);
hthread:=CreateThread(nil,0,@Tform1.MyThreadfunc,nil,0,ThreadID);
hthread:=CreateThread(nil,0,@Tform1.MyThreadfunc1,nil,0,ThreadID);
end;

end.
 
谢谢 ldsdelphibbs,请问我关闭系统的时候要不要释放呢?如果要的话那个函数是什么?
 
不是啊。我是说,我的线程创建如下:
hthread:=CreateThread(nil,0,@Tform1.MyThreadfunc,nil,0,ThreadID);
hthread:=CreateThread(nil,0,@Tform1.MyThreadfunc1,nil,0,ThreadID);
如果我要结束线程要用TerminateThread();同时要closehandle(hthread),closehandle(hthread1).那么为什么我已经关闭句柄后。句柄仍然存在且有时候会报错呢?
 
结束线程最好不要用TerminateThread(),而用ExitThread(),但是最好直接让它从线程中返回.至于你出的问题,这个要看具体的代码。
 
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls;
type
Tbuffer = record
SrsNo:String;
Srscont:string;
Rcvtime:Tdatetime;
tag:integer;
end;
TForm1 = class(TForm)
Button1: TButton;
Edit1: TEdit;
Edit2: TEdit;
Button2: TButton;
Label1: TLabel;
Label2: TLabel;
procedure Button1Click(Sender: TObject);
procedure FormCreate(Sender: TObject);
procedure FormClose(Sender: TObject;
var Action: TCloseAction);
private
{ Private declarations }
ThreadCount,ReadPos,WritePos:integer;
hThread,hThread1,ThreadID,ThreadID1:Thandle;
//定义句柄及ID
FFinished: Boolean;
//定义是否挂起
TempBuffer : array [0..255] of Tbuffer;
function MyThreadFunc(P:pointer):Longint;stdcall;
function MyThreadFunc1(P:pointer):Longint;stdcall;
public
InterlockedCrit : TRTLCriticalSection;
{ Public declarations }
end;
var
Form1: TForm1;
implementation
{$R *.dfm}
function Tform1.MyThreadFunc(P:pointer):Longint;stdcall;
var i:integer;
begin
while not application.Terminateddo
begin
sleep(100);
with Form1do
begin
EnterCriticalSection(InterlockedCrit);
if WritePos =256 then
WritePos := 0;
TempBuffer[WritePos].SrsNo := inttostr(i);
TempBuffer[WritePos].Srscont := inttostr(i);
TempBuffer[WritePos].Rcvtime := now;
edit1.Text := inttostr(i);
inc(WritePos);
inc(i);
LeaveCriticalSection(InterlockedCrit);
end;
end;
end;

function Tform1.MyThreadFunc1(P:pointer):Longint;stdcall;
begin
while not application.Terminateddo
begin
sleep(100);
with Form1do
begin
EnterCriticalSection(InterlockedCrit);
if Form1.ReadPos =256 then
ReadPos := 0;
edit2.Text := TempBuffer[ReadPos].SrsNo;
inc(ReadPos);
LeaveCriticalSection(InterlockedCrit);
end;
end;
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
if (hthread=0) and (hthread1=0) then
begin
InterlockedIncrement(ThreadCount);
hthread:=CreateThread(nil,0,@Tform1.MyThreadfunc,nil,0,ThreadID);
InterlockedIncrement(ThreadCount);
hthread1:=CreateThread(nil,0,@Tform1.MyThreadfunc1,nil,0,ThreadID1);
end
else
begin
CloseHandle(hThread);
CloseHandle(hThread1);
DeleteCriticalSection(InterlockedCrit);
InterlockedDecrement(ThreadCount);
InterlockedDecrement(ThreadCount);
end;
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
ThreadCount := 0;
InitializeCriticalSection(InterlockedCrit);
end;

procedure TForm1.FormClose(Sender: TObject;
var Action: TCloseAction);
begin
TerminateThread(hThread,ThreadID);
TerminateThread(hThread1,ThreadID1);
InterlockedDecrement(ThreadCount);
InterlockedDecrement(ThreadCount);
DeleteCriticalSection(InterlockedCrit);
end;
end.

请ldsdelphibb指教!谢谢!
 
closehandle(hthread)只是减少引用记数,线程如果不是强制被结束,即使计数为0也不会结束,要等到线程函数的工作做完才会结束。
 
那我该如何强制推出线程啊?
 
接受答案了.
 

Similar threads

后退
顶部