结束线程总 报System Error Code 6 句柄无效代码如下
-------
unit ChoseUnt;procedure TChoseFrm.Label4Click(Sender: TObject);
var
Frm: TOutDataFrm;
begin
FormTitle := '电子报税数据导出';
Frm := TOutDataFrm.Create(Self);
try
ChoseNum := 4;
Frm.ShowModal;
finally
Frm.Close;
end;
end;
-------------
unit OutDataUnt;procedure TOutDataFrm.Button3Click(Sender: TObject);
begin
if ThreadUnt.PubThred <> nil then
begin
ThreadUnt.PubThred.Terminate;
ThreadUnt.PubThred.WaitFor;
ThreadUnt.PubThred.Free;
end;
Button3.Enabled := False;
end;
procedure TOutDataFrm.ProcOutSearchData_dzbs;
var
DateFileStr, DateStr, BgDataStr, InsertSqlStr, EdDataStr, StrErr,
StrMsg, FieldStr, WrFileStr, selSql, s, ridStr: string;
AryNum, FieldNum, OdNum, i, p: Integer;
EveyNum: Double;
Qytmp: TADOQuery;
Ftext: TextFile;
begin
CommFuncUnt.ProcWriteFile('***************************************************************'
+ FuncGetDateStr, CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
CommFuncUnt.ProcWriteFile('开始导出表returnreceipt数据 时间:' +
FuncGetDateStr, CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName)); DateStr := copy(FuncGetVersion, 0, 8);
DateFileStr := FuncGetVersion; EveyNum := AllDataNum / 1000;
p := pos('.', FloattoStr(EveyNum));
s := copy(FloattoStr(EveyNum), 1, p - 1);
try
OdNum := StrToInt(s);
except
on e:
Exception do
begin
CommFuncUnt.ProcWriteFile('数据初试化失败',
CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
CommFuncUnt.ProcWriteFile('***************************************************************'
+ FuncGetDateStr, CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
StatusBar1.Panels[0].Text := '数据初试化失败';
button2.Enabled := True;
Screen.cursor := crDefault;
Exit;
end;
end;
Qytmp := DataModuleUnt.DataModule1.QyTmp1; ; AryNum := 0;
/////开始数据导入
//////打开文件
AssignFile(Ftext, Edit5.Text + '\returnreceipt_' + DateFileStr + '.txt');
rewrite(Ftext);
append(Ftext);
///////写入导出文件头
BgDataStr := 'BEGIN' + #13#10;
BgDataStr := BgDataStr + IntToStr(AllDataNum) + '~~returnreceipt' + #13#10;
BgDataStr := BgDataStr + '{' + #13#10;
BgDataStr := BgDataStr + '0~~' + IntToStr(AllDataNum + 2) +
'~~returnreceipt~~电子报税回执数据' + #13#10;
BgDataStr := BgDataStr + '1~~' + sjbh + '~~' + sjmc + '~~' + DateStr + #13#10;
BgDataStr := BgDataStr + '2~~3~~' + IntToStr(AllDataNum + 2);
//ProcWriteFile(BgDataStr, Edit5.Text + '\fapsj_' + DateFileStr + '.txt');
writeln(Ftext, BgDataStr);
//ProgressBar1.Max := length(SearchDataAry);
ProgressBar1.Max := AllDataNum; ///////写入导出文件体
for i := 0 to odNum do
begin
if i = 0 then
begin
selSql := 'SELECT substr(rowid||jitbm,0,18) as id, nasrnm, jitbm, youjrq, banbh, suosrq,';
selSql := selSql + 'biaom, shuizmc, fajrdz, shoujrdz, subject, msgtext,';
selSql := selSql + 'send_flag, shangcbz ';
selSql := selSql + 'FROM returnreceipt where rownum<1001';
end
else
begin
selSql := 'SELECT substr(rowid||jitbm,0,18) as id, nasrnm, jitbm, youjrq, banbh, suosrq,';
selSql := selSql + 'biaom, shuizmc, fajrdz, shoujrdz, subject, msgtext,';
selSql := selSql + 'send_flag, shangcbz ';
selSql := selSql + 'FROM returnreceipt where rownum<1001 and rowid>''' +
ridStr + '''';
end;
if AddSqlStr <> '' then
begin
Selsql := Selsql + ' and ' + AddSqlStr;
end;
//////--------------选出要导出的数据
if not CommFuncUnt.FuncExecSql(selSql, Qytmp, True, StrErr) then
begin
StrMsg := '执行SQL:' + selSql + '语句出错,错误原因:' + StrErr;
FuncShowMessage(Handle, StrMsg, 2);
CommFuncUnt.ProcWriteFile('数据初试化失败:' + StrMsg,
CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
CommFuncUnt.ProcWriteFile('***************************************************************'
+ FuncGetDateStr, CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
StatusBar1.Panels[0].Text := '数据初试化失败';
button2.Enabled := True;
Screen.cursor := crDefault;
Exit;
end;
WrFileStr := '';
try
while not Qytmp.EOF do
begin
FieldStr := IntToStr(aryNum + 3) + '~~';
for FieldNum := 1 to Qytmp.FieldCount - 1 do
begin
FieldStr := FieldStr + Qytmp.Fields[FieldNum].AsString + '~~';
end; FieldStr := copy(FieldStr, 0, length(FieldStr) - 2);
writeln(Ftext, FieldStr);
//WrFileStr := WrFileStr + FieldStr + #13#10;
InsertSqlStr :=
'update returnreceipt set shangcbz=decode(shangcbz,null,1,shangcbz+1) where rowid= ''' +
Qytmp.Fields[0].AsString + ''''; if not CommFuncUnt.FuncExecSql(InsertSqlStr,
DataModuleUnt.DataModule1.QyTmp2, False, StrErr) then
begin
StrMsg := '执行SQL:' + InsertSqlStr + '语句出错,错误原因:' + StrErr;
FuncShowMessage(Handle, StrMsg, 2);
button1.Enabled := True;
Screen.cursor := crDefault;
CommFuncUnt.ProcWriteFile('导出表returnreceipt数据失败 时间:' +
FuncGetDateStr, CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
CommFuncUnt.ProcWriteFile('失败原因:' + StrMsg,
CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
CommFuncUnt.ProcWriteFile('***************************************************************'
+ FuncGetDateStr, CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
Closefile(Ftext);
DeleteFile(Edit5.Text + '\returnreceipt_' + DateFileStr + '.txt');
Exit;
end;
inc(AryNum);
ProgressBar1.Position := AryNum;
StatusBar1.SimpleText := '正在导出第' + IntToStr(AryNum) + '条数据';
FieldStr := '';
ridStr := Qytmp.FieldByName('id').AsString;
Qytmp.Next; //////退出
if ThreadUnt.PubThred.Terminated then
begin
Closefile(Ftext);
Qytmp.Close;
DeleteFile(Edit5.Text + '\returnreceipt_' + DateFileStr + '.txt');
button1.Enabled := True;
Screen.cursor := crDefault;
StatusBar1.SimpleText := '导出中断';
ProgressBar1.Position := 0;
Exit;
end;
//////
end;
except
on e:
Exception do
begin
end;
end;
end;
Qytmp.Close; EdDataStr := EdDataStr + '}' + #13#10;
EdDataStr := EdDataStr + 'END';
//ProcWriteFile(EdDataStr, Edit5.Text + '\fapsj_' + DateFileStr + '.txt');
writeln(Ftext, EdDataStr);
////////////////数据导出完毕
StatusBar1.Panels[0].Text := '共导出' + IntToStr(AllDataNum) + '条数据';
closefile(Ftext);
Screen.cursor := crDefault;
button2.Enabled := True;
CommFuncUnt.ProcWriteFile('共导出' + IntToStr(AllDataNum) + '条数据',
CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
CommFuncUnt.ProcWriteFile('导出表returnreceipt数据结束 时间:' +
FuncGetDateStr, CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
CommFuncUnt.ProcWriteFile('***************************************************************'
+ FuncGetDateStr, CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
end;
-------
unit ChoseUnt;procedure TChoseFrm.Label4Click(Sender: TObject);
var
Frm: TOutDataFrm;
begin
FormTitle := '电子报税数据导出';
Frm := TOutDataFrm.Create(Self);
try
ChoseNum := 4;
Frm.ShowModal;
finally
Frm.Close;
end;
end;
-------------
unit OutDataUnt;procedure TOutDataFrm.Button3Click(Sender: TObject);
begin
if ThreadUnt.PubThred <> nil then
begin
ThreadUnt.PubThred.Terminate;
ThreadUnt.PubThred.WaitFor;
ThreadUnt.PubThred.Free;
end;
Button3.Enabled := False;
end;
procedure TOutDataFrm.ProcOutSearchData_dzbs;
var
DateFileStr, DateStr, BgDataStr, InsertSqlStr, EdDataStr, StrErr,
StrMsg, FieldStr, WrFileStr, selSql, s, ridStr: string;
AryNum, FieldNum, OdNum, i, p: Integer;
EveyNum: Double;
Qytmp: TADOQuery;
Ftext: TextFile;
begin
CommFuncUnt.ProcWriteFile('***************************************************************'
+ FuncGetDateStr, CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
CommFuncUnt.ProcWriteFile('开始导出表returnreceipt数据 时间:' +
FuncGetDateStr, CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName)); DateStr := copy(FuncGetVersion, 0, 8);
DateFileStr := FuncGetVersion; EveyNum := AllDataNum / 1000;
p := pos('.', FloattoStr(EveyNum));
s := copy(FloattoStr(EveyNum), 1, p - 1);
try
OdNum := StrToInt(s);
except
on e:
Exception do
begin
CommFuncUnt.ProcWriteFile('数据初试化失败',
CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
CommFuncUnt.ProcWriteFile('***************************************************************'
+ FuncGetDateStr, CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
StatusBar1.Panels[0].Text := '数据初试化失败';
button2.Enabled := True;
Screen.cursor := crDefault;
Exit;
end;
end;
Qytmp := DataModuleUnt.DataModule1.QyTmp1; ; AryNum := 0;
/////开始数据导入
//////打开文件
AssignFile(Ftext, Edit5.Text + '\returnreceipt_' + DateFileStr + '.txt');
rewrite(Ftext);
append(Ftext);
///////写入导出文件头
BgDataStr := 'BEGIN' + #13#10;
BgDataStr := BgDataStr + IntToStr(AllDataNum) + '~~returnreceipt' + #13#10;
BgDataStr := BgDataStr + '{' + #13#10;
BgDataStr := BgDataStr + '0~~' + IntToStr(AllDataNum + 2) +
'~~returnreceipt~~电子报税回执数据' + #13#10;
BgDataStr := BgDataStr + '1~~' + sjbh + '~~' + sjmc + '~~' + DateStr + #13#10;
BgDataStr := BgDataStr + '2~~3~~' + IntToStr(AllDataNum + 2);
//ProcWriteFile(BgDataStr, Edit5.Text + '\fapsj_' + DateFileStr + '.txt');
writeln(Ftext, BgDataStr);
//ProgressBar1.Max := length(SearchDataAry);
ProgressBar1.Max := AllDataNum; ///////写入导出文件体
for i := 0 to odNum do
begin
if i = 0 then
begin
selSql := 'SELECT substr(rowid||jitbm,0,18) as id, nasrnm, jitbm, youjrq, banbh, suosrq,';
selSql := selSql + 'biaom, shuizmc, fajrdz, shoujrdz, subject, msgtext,';
selSql := selSql + 'send_flag, shangcbz ';
selSql := selSql + 'FROM returnreceipt where rownum<1001';
end
else
begin
selSql := 'SELECT substr(rowid||jitbm,0,18) as id, nasrnm, jitbm, youjrq, banbh, suosrq,';
selSql := selSql + 'biaom, shuizmc, fajrdz, shoujrdz, subject, msgtext,';
selSql := selSql + 'send_flag, shangcbz ';
selSql := selSql + 'FROM returnreceipt where rownum<1001 and rowid>''' +
ridStr + '''';
end;
if AddSqlStr <> '' then
begin
Selsql := Selsql + ' and ' + AddSqlStr;
end;
//////--------------选出要导出的数据
if not CommFuncUnt.FuncExecSql(selSql, Qytmp, True, StrErr) then
begin
StrMsg := '执行SQL:' + selSql + '语句出错,错误原因:' + StrErr;
FuncShowMessage(Handle, StrMsg, 2);
CommFuncUnt.ProcWriteFile('数据初试化失败:' + StrMsg,
CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
CommFuncUnt.ProcWriteFile('***************************************************************'
+ FuncGetDateStr, CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
StatusBar1.Panels[0].Text := '数据初试化失败';
button2.Enabled := True;
Screen.cursor := crDefault;
Exit;
end;
WrFileStr := '';
try
while not Qytmp.EOF do
begin
FieldStr := IntToStr(aryNum + 3) + '~~';
for FieldNum := 1 to Qytmp.FieldCount - 1 do
begin
FieldStr := FieldStr + Qytmp.Fields[FieldNum].AsString + '~~';
end; FieldStr := copy(FieldStr, 0, length(FieldStr) - 2);
writeln(Ftext, FieldStr);
//WrFileStr := WrFileStr + FieldStr + #13#10;
InsertSqlStr :=
'update returnreceipt set shangcbz=decode(shangcbz,null,1,shangcbz+1) where rowid= ''' +
Qytmp.Fields[0].AsString + ''''; if not CommFuncUnt.FuncExecSql(InsertSqlStr,
DataModuleUnt.DataModule1.QyTmp2, False, StrErr) then
begin
StrMsg := '执行SQL:' + InsertSqlStr + '语句出错,错误原因:' + StrErr;
FuncShowMessage(Handle, StrMsg, 2);
button1.Enabled := True;
Screen.cursor := crDefault;
CommFuncUnt.ProcWriteFile('导出表returnreceipt数据失败 时间:' +
FuncGetDateStr, CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
CommFuncUnt.ProcWriteFile('失败原因:' + StrMsg,
CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
CommFuncUnt.ProcWriteFile('***************************************************************'
+ FuncGetDateStr, CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
Closefile(Ftext);
DeleteFile(Edit5.Text + '\returnreceipt_' + DateFileStr + '.txt');
Exit;
end;
inc(AryNum);
ProgressBar1.Position := AryNum;
StatusBar1.SimpleText := '正在导出第' + IntToStr(AryNum) + '条数据';
FieldStr := '';
ridStr := Qytmp.FieldByName('id').AsString;
Qytmp.Next; //////退出
if ThreadUnt.PubThred.Terminated then
begin
Closefile(Ftext);
Qytmp.Close;
DeleteFile(Edit5.Text + '\returnreceipt_' + DateFileStr + '.txt');
button1.Enabled := True;
Screen.cursor := crDefault;
StatusBar1.SimpleText := '导出中断';
ProgressBar1.Position := 0;
Exit;
end;
//////
end;
except
on e:
Exception do
begin
end;
end;
end;
Qytmp.Close; EdDataStr := EdDataStr + '}' + #13#10;
EdDataStr := EdDataStr + 'END';
//ProcWriteFile(EdDataStr, Edit5.Text + '\fapsj_' + DateFileStr + '.txt');
writeln(Ftext, EdDataStr);
////////////////数据导出完毕
StatusBar1.Panels[0].Text := '共导出' + IntToStr(AllDataNum) + '条数据';
closefile(Ftext);
Screen.cursor := crDefault;
button2.Enabled := True;
CommFuncUnt.ProcWriteFile('共导出' + IntToStr(AllDataNum) + '条数据',
CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
CommFuncUnt.ProcWriteFile('导出表returnreceipt数据结束 时间:' +
FuncGetDateStr, CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
CommFuncUnt.ProcWriteFile('***************************************************************'
+ FuncGetDateStr, CommFuncUnt.FuncGetLogFile(Unit_DbtoFLogFileName));
end;
Terminate;
ThreadUnt.PubThred.WaitFor;
ThreadUnt.PubThred.Free;
这样的。
如果要强制kill这样写线程的FreeOnTerminate设成False
然后Thread.Free;最好的方法是
线程的FreeOnTerminate设成True
然后然后在线程中经常判断Terminated
终止线程用Thread.Terminate
begin
inherited Create(false);
PrStr := s;
Self.FreeOnTerminate := true;
end;destructor ThredUnt.destroy;
begin
//PubThred := nil;
inherited destroy;
end;procedure ThredUnt.DoTerminate;
begin
inherited;
PubThred := nil;
end;procedure ThredUnt.Execute;
begin
if PrStr = 'SearchData' then
OutDatafrm.ProcSearchData
else if PrStr = 'OutSearchData' then
OutDatafrm.ProcOutSearchData
else if PrStr = 'DatatoDb' then
InDatafrm.ProcDataToDb
else if PrStr = 'SearchData_dzbs' then
OutDatafrm.ProcSearchData_dzbs
else if PrStr = 'OutSearchData_dzbs' then
OutDatafrm.ProcOutSearchData_dzbs
else if PrStr = 'DatatoDb_dzbs' then
InDatafrm.ProcDataToDb_dzbs
else if PrStr = 'SelDelData' then
DelDatafrm.ProcSelDelData
else if PrStr = 'DelSelData' then
DelDatafrm.ProcDelSelData
else
PubThred := nil; { Place thread code here }
end;
然后Thread.Free;
不用terminate然后waitfor
虽然该方法不大好,但是至少不会报错最好的方法是线程自己释放,那么你的
ProcOutSearchData_dzbs
ProcSelDelData
这些过程就要判断thread.Terminated,如果Terminated,就要exit退出,这样线程就自己释放了
Thread.Free;
就手工释放了,否则系统自动释放的时候会报错,因为已经被你手工释放了