本人做了一个系统.要求用Dephi开发.利用ADO进很多线程数据库连接,请问如何实现,我己完成了大部分.下面是一个线程的代码
unit uMSUImport;interfaceuses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, DB, ADODB, StdCtrls, Buttons,inifiles, ExtCtrls, FileCtrl;
type
TMSUImport = class(TThread)
private
AdoConn: TAdoConnection;
FileList :TStringList;
IniFile :TIniFile;
LastFileValue :Int64;
strDirectory :String;
CurrFileName :String;
strIniFileName:String;
Procedure WriteLastRecord(strRecordTime:String);
function CreateLog(var strSource,strTarget:String):String; procedure GetFileList(var iMinFileName:int64);
procedure WriteIniFile();
procedure ReadIniFile();
procedure CreateMSUTable(var MSUTableName:String);
procedure StartMSUImport; procedure WriteLogFile(var strlog:String);
procedure MSUImport(var MSUFileName,MSUTableName:String); public
constructor Create(strConn:String);
protected
procedure Execute; override;
end;implementation
uses ufrmAutoImport;constructor TMSUImport.Create(strConn:String);
begin
inherited Create(True);
AdoConn:=TAdoConnection.Create(Application);
AdoConn.Connected:=False;
AdoConn.LoginPrompt:=False;
AdoConn.ConnectionString:=strConn;
AdoConn.ConnectOptions:=coConnectUnspecified;
AdoConn.Open;
FileList:=TStringList.Create;
end;
procedure TMSUImport.Execute;
begin
FreeOnTerminate:=True;
StartMSUImport;
end;
procedure TMSUImport.WriteIniFile();
begin
IniFile:=TiniFile.Create(strIniFileName);
IniFile.WriteString('STATE','LASTMSU',CurrFileName);
IniFile.Free;
end;procedure TMSUImport.ReadIniFile();
varstrTemp:String ;
begin
strIniFileName:=ChangeFileExt(Application.ExeName,'.INI');
IniFile:=TiniFile.Create(strIniFileName);
strDirectory:=IniFile.ReadString('Dir','MSUDir','C:\');
strTemp:=IniFile.ReadString('STATE','LASTMSU','000000000000');
if strTemp='' then strTemp:='0';
CurrFileName:=strTemp;
strTemp:=Copy(strTemp,1,8);
LastFileValue:=strToInt64(strTemp);
IniFile.Free;
end;
procedure TMSUImport.GetFileList(var iMinFileName:int64);
var
sr: TSearchRec;
FileAttrs:Integer;
strFileName:String;
strTemp:String;
iTemp:Int64;
begin FileList.Clear;
StrFileName:= strDirectory+'\*.MSU';
FileAttrs:=faAnyFile;
if FindFirst(StrFileName, FileAttrs, sr) = 0 then begin
repeat
if (sr.Attr and FileAttrs) = sr.Attr then
begin
strTemp:=Copy(sr.Name,1,8);
iTemp:=StrToInt64(strTemp);
if iTemp>iMinFilename then
FileList.Append(sr.Name);
end;
until FindNext(sr) <> 0;
end;
FileList.Sort;end;
//////////////////////////StartMSU///////////////////////
procedure TMSUImport.StartMSUImport;
var
strlog:String;
strTableName:String;
FullFileName:String; nCount:Integer;begin
/////////// 查找该入库的文件名///////////////////////////////////////
ReadIniFile;
GetFileList(LastFileValue);
////////////////////入库 /////////////////////////////////////////// for nCount:=1 To FileList.Count-1 do
begin
if frmAutoImport.ThreadCommand=false then break;
WriteIniFile;
CurrFileName:=FileList.Strings[nCount];
strTableName:='T_MSU'+Copy(CurrFileName,1,6);
CreateMSUTable(strTableName); strlog:=CreateLog(CurrFileName,strTableName);
FullFileName:=strDirectory+'\'+CurrFilename; WriteLogFile(strlog);
MSUImport(FullFileName,strTableName);
//WriteIniFile;
end; //////////////////保存最后所读文件记录////////////////////////////////
WriteIniFile;
try
AdoConn.close;
finally
end;
end;
function TMSUImport.CreateLog(var strSource,strTarget:String):String;var
strOperate:String;
strlog:String;begin
strOperate:='MSU数据导入';
strlog:=DateTimeToStr(now());
strlog:=strlog+' ';
strlog:=strlog+strOperate;
strlog:=strlog+' ';
strlog:=strlog+strSource;
strlog:=strlog+' ';
strlog:=strlog+strTarget;
Result:=strlog;
end;procedure TMSUImport.WriteLogFile(var strlog:String);
begin
writeln(ufrmAutoImport.frmAutoImport.logFile,strlog);
end;procedure TMSUImport.MSUImport(var MSUFileName,MSUTableName:String);
var
MSUFile:textfile;
strLine:String;
strSql:String;begin
assignfile(MSUFile,MSUFileName);
ReSet(MSUFile); while not Eof(MSUFile) do
begin
ReadLn(MSUFile,strLine); ///////////////////追加MSU记录到数据库中///////////////////////////////// strSql:='Insert '+MSUTableName+'(StartTime,MSUCnt,MSULen) ';
strSql:=strSql+'Values('''+Copy(StrLine,1,18)+''','+Trim(Copy(strLine,21,9))+',';
strSql:=strSql+Trim(Copy(strLine,32,9))+')';
adoConn.Execute(strSql);
Application.ProcessMessages; end;
WriteLastRecord(Copy(StrLine,1,18));
CloseFile(MSUFile);end;Procedure TMSUImport.WriteLastRecord(strRecordTime:String);
begin
IniFile:=TiniFile.Create(strIniFileName);
IniFile.WriteString('LASTRECORD','LastMSURecord',strRecordTime);
IniFile.Free;
end;procedure TMSUImport.CreateMSUTable(var MSUTableName:String);
var
strSql:String;
begin
strSql:='if not exists (select * from dbo.sysobjects where id =';
strSql:=strSql+' object_id(N''[dbo].['+MSUTableName+']'') ';
strSql:=strSql+'and OBJECTPROPERTY(id, N''IsUserTable'') = 1)';
strSql:=strSql+'CREATE TABLE [dbo].['+MSUTableName+'] (';
strSql:=strSql+'[RecordID] [int] IDENTITY (1, 1) NOT NULL ,';
strSql:=strSql+'[StartTime] [datetime] NOT NULL ,';
strSql:=strSql+'[MSUCnt] [int] NULL ,';
strSql:=strSql+'[MSULen] [int] NULL';
strSql:=StrSql+') ON [PRIMARY]';
AdoConn.Execute(strSql);
end;
end.但是该代码会多现下面的问题.
本程序要求3个类似的线程同时执行.只是SQL语句部分不同.如果所有线程执行完成后.关闭程序.一切正常.如查线程还在执行就关闭程序.则会引发异常,提示为,在异步情况下不能执行.即使是强制关闭线程也不行.估计是异步连接是不可控制不能强行关闭.但是在我无法强制设定TAdoConnection的连接方试为同步.导步倒是可以..所以现在我只好设定先停止线程再关闭程序.中间等待20秒,问题就不会出现.可是这是不合要求的.希望那位高手指点一下.谢谢
unit uMSUImport;interfaceuses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, DB, ADODB, StdCtrls, Buttons,inifiles, ExtCtrls, FileCtrl;
type
TMSUImport = class(TThread)
private
AdoConn: TAdoConnection;
FileList :TStringList;
IniFile :TIniFile;
LastFileValue :Int64;
strDirectory :String;
CurrFileName :String;
strIniFileName:String;
Procedure WriteLastRecord(strRecordTime:String);
function CreateLog(var strSource,strTarget:String):String; procedure GetFileList(var iMinFileName:int64);
procedure WriteIniFile();
procedure ReadIniFile();
procedure CreateMSUTable(var MSUTableName:String);
procedure StartMSUImport; procedure WriteLogFile(var strlog:String);
procedure MSUImport(var MSUFileName,MSUTableName:String); public
constructor Create(strConn:String);
protected
procedure Execute; override;
end;implementation
uses ufrmAutoImport;constructor TMSUImport.Create(strConn:String);
begin
inherited Create(True);
AdoConn:=TAdoConnection.Create(Application);
AdoConn.Connected:=False;
AdoConn.LoginPrompt:=False;
AdoConn.ConnectionString:=strConn;
AdoConn.ConnectOptions:=coConnectUnspecified;
AdoConn.Open;
FileList:=TStringList.Create;
end;
procedure TMSUImport.Execute;
begin
FreeOnTerminate:=True;
StartMSUImport;
end;
procedure TMSUImport.WriteIniFile();
begin
IniFile:=TiniFile.Create(strIniFileName);
IniFile.WriteString('STATE','LASTMSU',CurrFileName);
IniFile.Free;
end;procedure TMSUImport.ReadIniFile();
varstrTemp:String ;
begin
strIniFileName:=ChangeFileExt(Application.ExeName,'.INI');
IniFile:=TiniFile.Create(strIniFileName);
strDirectory:=IniFile.ReadString('Dir','MSUDir','C:\');
strTemp:=IniFile.ReadString('STATE','LASTMSU','000000000000');
if strTemp='' then strTemp:='0';
CurrFileName:=strTemp;
strTemp:=Copy(strTemp,1,8);
LastFileValue:=strToInt64(strTemp);
IniFile.Free;
end;
procedure TMSUImport.GetFileList(var iMinFileName:int64);
var
sr: TSearchRec;
FileAttrs:Integer;
strFileName:String;
strTemp:String;
iTemp:Int64;
begin FileList.Clear;
StrFileName:= strDirectory+'\*.MSU';
FileAttrs:=faAnyFile;
if FindFirst(StrFileName, FileAttrs, sr) = 0 then begin
repeat
if (sr.Attr and FileAttrs) = sr.Attr then
begin
strTemp:=Copy(sr.Name,1,8);
iTemp:=StrToInt64(strTemp);
if iTemp>iMinFilename then
FileList.Append(sr.Name);
end;
until FindNext(sr) <> 0;
end;
FileList.Sort;end;
//////////////////////////StartMSU///////////////////////
procedure TMSUImport.StartMSUImport;
var
strlog:String;
strTableName:String;
FullFileName:String; nCount:Integer;begin
/////////// 查找该入库的文件名///////////////////////////////////////
ReadIniFile;
GetFileList(LastFileValue);
////////////////////入库 /////////////////////////////////////////// for nCount:=1 To FileList.Count-1 do
begin
if frmAutoImport.ThreadCommand=false then break;
WriteIniFile;
CurrFileName:=FileList.Strings[nCount];
strTableName:='T_MSU'+Copy(CurrFileName,1,6);
CreateMSUTable(strTableName); strlog:=CreateLog(CurrFileName,strTableName);
FullFileName:=strDirectory+'\'+CurrFilename; WriteLogFile(strlog);
MSUImport(FullFileName,strTableName);
//WriteIniFile;
end; //////////////////保存最后所读文件记录////////////////////////////////
WriteIniFile;
try
AdoConn.close;
finally
end;
end;
function TMSUImport.CreateLog(var strSource,strTarget:String):String;var
strOperate:String;
strlog:String;begin
strOperate:='MSU数据导入';
strlog:=DateTimeToStr(now());
strlog:=strlog+' ';
strlog:=strlog+strOperate;
strlog:=strlog+' ';
strlog:=strlog+strSource;
strlog:=strlog+' ';
strlog:=strlog+strTarget;
Result:=strlog;
end;procedure TMSUImport.WriteLogFile(var strlog:String);
begin
writeln(ufrmAutoImport.frmAutoImport.logFile,strlog);
end;procedure TMSUImport.MSUImport(var MSUFileName,MSUTableName:String);
var
MSUFile:textfile;
strLine:String;
strSql:String;begin
assignfile(MSUFile,MSUFileName);
ReSet(MSUFile); while not Eof(MSUFile) do
begin
ReadLn(MSUFile,strLine); ///////////////////追加MSU记录到数据库中///////////////////////////////// strSql:='Insert '+MSUTableName+'(StartTime,MSUCnt,MSULen) ';
strSql:=strSql+'Values('''+Copy(StrLine,1,18)+''','+Trim(Copy(strLine,21,9))+',';
strSql:=strSql+Trim(Copy(strLine,32,9))+')';
adoConn.Execute(strSql);
Application.ProcessMessages; end;
WriteLastRecord(Copy(StrLine,1,18));
CloseFile(MSUFile);end;Procedure TMSUImport.WriteLastRecord(strRecordTime:String);
begin
IniFile:=TiniFile.Create(strIniFileName);
IniFile.WriteString('LASTRECORD','LastMSURecord',strRecordTime);
IniFile.Free;
end;procedure TMSUImport.CreateMSUTable(var MSUTableName:String);
var
strSql:String;
begin
strSql:='if not exists (select * from dbo.sysobjects where id =';
strSql:=strSql+' object_id(N''[dbo].['+MSUTableName+']'') ';
strSql:=strSql+'and OBJECTPROPERTY(id, N''IsUserTable'') = 1)';
strSql:=strSql+'CREATE TABLE [dbo].['+MSUTableName+'] (';
strSql:=strSql+'[RecordID] [int] IDENTITY (1, 1) NOT NULL ,';
strSql:=strSql+'[StartTime] [datetime] NOT NULL ,';
strSql:=strSql+'[MSUCnt] [int] NULL ,';
strSql:=strSql+'[MSULen] [int] NULL';
strSql:=StrSql+') ON [PRIMARY]';
AdoConn.Execute(strSql);
end;
end.但是该代码会多现下面的问题.
本程序要求3个类似的线程同时执行.只是SQL语句部分不同.如果所有线程执行完成后.关闭程序.一切正常.如查线程还在执行就关闭程序.则会引发异常,提示为,在异步情况下不能执行.即使是强制关闭线程也不行.估计是异步连接是不可控制不能强行关闭.但是在我无法强制设定TAdoConnection的连接方试为同步.导步倒是可以..所以现在我只好设定先停止线程再关闭程序.中间等待20秒,问题就不会出现.可是这是不合要求的.希望那位高手指点一下.谢谢
解决方案 »
- 初学delphi,简单问题求解
- XP新建用户 怎么不在登录界面显示啊?
- DELPHI2006中有没有自带做报表的控件?
- 请问"=B0=A8=A4=C7=B7j=B4M"是什么字符表现格式??
- 用Delphi编写的禁止Ctrl+Alt+Delete热键钩子(线程注入)
- 为什么关闭delphi程序时出现堆栈溢出错误?
- 笔记:Delphi7下用dbExpress调用Oracle存储过程(返回数据集)的一个简单示例和调试过程
- 怎么怎么用SQL实现以下功能?
- 请指教!分不够可以再给……
- 用SHGetFileInfo乱码了
- delphi中的堆栈错误
- 非常急迫的问题:关于数据缓存更新保存中遇到的问题!(急!急!)
思想是:在线程结束时候发线程结束消息,然后在调用本线程的程序里做
WM_THREADDONE消息处理判断刚结束的线程代号是否是本线程,是则结束并等待它结束。
代码大概是:
MyThread.Terminate;
MyThread.WatiFor;
找到了:\Borland\delphi5\Help\Examples\Prgrsbar
就这个例子!:)