各位高手请帮我看一下我得多线程代码是否安全? 都有分!!(50分)

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

shadowno

Unregistered / Unconfirmed
GUEST, unregistred user!
unit Umywritedb;
interface
uses
Classes,ufuntion,udm,Dialogs,Sysutils,uviewsendstate;
const InStationFormat:string = '12444';
OutStationFormat:string = '124';
type
Tmywritedb = class(TThread)
private
Ustationcode:string;//车站编号
Ubuscode: string;
//车辆编号
Udrivercode:string;
// 驾驶员编号
Ubustypecode: integer;
// 车类型编号
Ubussendsort:integer;//车辆的发车序号与排班表对应;
Usendtime0: Tdatetime;
// 出始发站时间
Usendtime: Tdatetime;
// 出终点站时间
Uintotime0: Tdatetime;
// 进始发站时间
Uintotime: Tdatetime;
// 进终点站时间
Usyssendtime:Tdatetime;
// 系统自动发车时间
Urealsendtime:Tdatetime;
// 没用
{ Private declarations }
protected
procedure writedb;
function SerialToCode(USerial:string):string;
procedure Execute;
override;
public
ubusstate:Tmybusstate;
retrieveddata:string;
constructor Create(sbus:string);
// 构造函数
end;

implementation
uses sbmain;
constructor Tmywritedb.Create(sbus:string);
begin
retrieveddata:=sbus;
with fdmdo
begin
qserial.DatabaseName :='currentdb';
qserial.SessionName := 'dbsession';
end;
inherited Create(True);
end;

procedure Tmywritedb.writedb;
begin
with ubusstatedo
begin
if copy(retrieveddata,1,1)='<' then
begin
stationcode:='<';
buscode:=SerialToCode(copy(retrieveddata,2,3));
sendtime0:=StrToTime(copy(retrieveddata,5,2)+':'+copy(retrieveddata,7,2));
outstation(ubusstate,fdm.qserial,fviewsendstate.Memo1);
fviewsendstate.changesqltext(fviewsendstate.PageControl1.ActivePage.PageIndex);
fmain.comm1.WriteCommData(pchar('-'+buscode),4);
terminate;
end;

if copy(retrieveddata,1,1)='>' then
begin
stationcode:='>';
buscode:=SerialToCode(copy(retrieveddata,2,3));
if u_ReturnOutTime(buscode,fdm.qserial,fdm.dserial,now()) then
terminate;
//检测是否为假的进站信息。
intotime:=StrToTime(copy(retrieveddata,5,2)+':'+copy(retrieveddata,7,2));
sendtime:=StrToTime(copy(retrieveddata,9,2)+':'+copy(retrieveddata,11,2));
intotime0 :=StrToTime(copy(retrieveddata,13,2)+':'+copy(retrieveddata,15,2));
intostation(ubusstate,fdm.qserial,fviewsendstate.Memo1);
MoveRecordToHistory(buscode,fdm.qmovedata,fdm.dmovedata);
fviewsendstate.changesqltext(fviewsendstate.PageControl1.ActivePage.PageIndex);
fmain.comm1.WriteCommData(pchar('-'+buscode),4);
terminate;
end;
end;
end;


function Tmywritedb.SerialToCode(USerial:string):string;
var ls_buscode:string;
begin
with udm.fdmdo
begin
qserial.close;
qserial.SQL.Clear;
qserial.SQL.Add('SELECT k_busSerial.kbuscode '+
'FROM k_busSerial '+
'WHERE k_busSerial.kserial = '''+USerial+'''');
dserial.DataSet := qserial;
qserial.Open;
qserial.First ;
ls_buscode:=qserial.fieldbyname('kbuscode').asstring;
if Length(ls_buscode)<1 then
begin
showmessage('该车序号不存在,请与系统管理员联系!!!');
terminate;
end;
result:=ls_buscode;
end;
end;

procedure Tmywritedb.Execute;
begin
repeat
Synchronize(writedb);
until terminated;
end;
end.
 
可能存在问题哦,因为在你的线程里,对数据库控件的访问是访问的全局的,一种更安全的
做法是在线程内使用这些数据库控件的引用,当然在你的构造函数中就要把需要用到的这些
数据库控件以引用的方式传递到线程中,通过引用来操作数据库。
另外,你传递给线程的字符串,如果在线程中的其它地方不改变的话,retrieveddata会
始终等于sbus的,如果这个字符串满足你的条件,那么你的线程执行体会一直不停的执行,
你始终在操作同一条记录,几乎可以说是陷入了死循环。如果你的线程体不用循环,也就是
让线程体仅执行一次,那是不会出现死循环的情况的。
 
我对数据库不熟悉,但是我觉得你的Create应该改一下
constructor Tmywritedb.Create(sbus:string);
begin
inherited Create(True);
retrieveddata:=sbus;
with fdmdo
begin
qserial.DatabaseName :='currentdb';
qserial.SessionName := 'dbsession';
end;
resume;
end;

然后,在加入destroy
destructor destroy;override;
 
这个方法确实不错
 
补充一点:
你如果是多线程,并且这几个线程有相同代码,你需要使用互斥等来把这部分代码进行互斥
保护!
你到:http://www.delphibbs.com/delphibbs/dispq.asp?lid=1233274 去看看,那里有我
关于线程同步的一点建议!
 
是吗!!我去看看!!
 
呵呵 ,,兄台在线啊,
这里有原码!
http://www.delphibbs.com/delphibbs/dispq.asp?lid=1239764
 
后退
顶部