如何删除二进制流文件中的某条记录(小难),马上给分 如何删除二进制流文件中的某条记录(小难)比如第 i 条,谢谢, 解决方案 » 免费领取超大流量手机卡,每月29元包185G流量+100分钟通话, 中国电信官方发货 你有很多书放在箱子里(例如有5本),那么怎么把放在箱子里第3本书拿出来呢?首先你要把第5,4,3本拿出来,然后再把5,4放进去。删除记录也是类似的例如你有10条记录,要删除第4条,那么就要把,第5条记录写到第4条记录的位置,第6条写到第5条的位置,依此类推,当然最后第9和10条中都是原来第10条的信息,现在就要把文件缩短。使用API函数 SetEndofFile(FileStream.Handle);该API函数的作用是把流文件中当前指针所指向的位置设置为文件结束,所以,调用该函数时,你的记录指针应该指向第9条记录的结束出,第10条记录的开始处。ok,收工! procedure tjzck_form.DStreamData(FileName:String; StartPos,EndPos: Integer);//StartPos: 从此开始“删除”信息,EndPos: 到此结束“删除”信息//如果输入文件名与输出文件名相同,就等于把源文件的StartPos与EndPos之间的内容删除下面程序中 mssr_stream 是原来的要删除记录的文件流,已经打开,请指出错误,谢谢var Tmp: TMemoryStream;begin try// Ori := TFileStream.Create(FileName, fmOpenRead); Tmp := TMemoryStream.Create; Tmp.CopyFrom(mssr_stream, StartPos); //Tmp从Ori拷贝数据,但在StartPos与EndPos之间不拷,因此形同删除了一段数据 mssr_stream.Seek(EndPos,soFromBeginning); Tmp.CopyFrom(mssr_stream, mssr_stream.Size-EndPos); Tmp.SaveToStream(mssr_stream); //在此设置输出文件名 finally FreeAndNil(Tmp); end;end; 你使用内存流临时存放文件有一个很大的坏处就是当文件很大的时候,太占内存了。procedure tjzck_form.DStreamData(FileName:String; StartPos,EndPos: Integer);var Buffer: array[0..10239] of Byte; //开辟1M缓存 ReadCount, Pos1, Pos2: Integer;begin try Pos1 := StartPos; Pos2 := EndPos; repeat mssr_stream.Seek(Pos2,soFromBeginning); Pos2 := Pos2 + 10240; ReadCount := mssr_stream.Read(Buffer, 10240); if ReadCount > 0 then begin mssr_stream.Seek(Pos1, soFromBeginning); mssr_stream.Write(Buffer, 10240); Pos1 := Pos1 + 10240; end; until ReadCount <= 0; mssr_stream.Seek(-(StartPos-EndPos), soFromEnd); SetEndOfFile(mssr_stream); finally mssr_stream.Free; end;end; SetEndOfFile(mssr_stream);行错误如下,[Error] jzck_unit.pas(122): Incompatible types: 'Cardinal' and 'TRecordStream1' 我把SetEndOfFile(mssr_stream);屏蔽,执行后变成拷贝了一大堆乱码,。非常多 我把SetEndOfFile(mssr_stream) 改成 SetEndOfFile(mssr_stream.Handle); 还是一大堆乱码。谢谢 sorry!mssr_stream.Write(Buffer, 10240);改为:mssr_stream.Write(Buffer, ReadCount);SetEndOfFile(mssr_stream)改为SetEndOfFile(mssr_stream.Handle);再看看!嘻嘻,信手写不行,哎 哦!还要改一句Pos1 := Pos1 + ReadCount;没你那个流,没办法测试,真麻烦,再看看! spcomm控件的问题 谁用过“东洋近视治疗仪”?我有急用!网址是哪里?google里都找不到!谢谢大家了!!! 小弟在Delphi版的第一贴:如何编程获得用户对文件的新建、复制、删除等操作!!! 如何安装msdn 关于自增长型字段是否总有一天可能溢出的简单问题!请教各位大虾,急!在线等待!解决完立刻结帖! 如何让TPanel有滚动条? 请问:BDE和ADO的区别? AdoDataset 得 Eof 是怎么回事 CSDN改版后的问题 关于delphi反编译 【请教】 如何操作一个Unicode的文本文件? 数据一致性问题!共3种,请问分别怎样解决?
删除记录也是类似的例如你有10条记录,要删除第4条,那么就要把,第5条记录写到第4条记录的位置,第6条写到第5条的位置,依此类推,
当然最后第9和10条中都是原来第10条的信息,现在就要把文件缩短。
使用API函数 SetEndofFile(FileStream.Handle);
该API函数的作用是把流文件中当前指针所指向的位置设置为文件结束,所以,调用该函数时,你的记录指针应该指向第9条记录的结束出,第10条记录的开始处。ok,收工!
//StartPos: 从此开始“删除”信息,EndPos: 到此结束“删除”信息
//如果输入文件名与输出文件名相同,就等于把源文件的StartPos与EndPos之间的内容删除
下面程序中 mssr_stream 是原来的要删除记录的文件流,已经打开,请指出错误,谢谢
var
Tmp: TMemoryStream;
begin
try
// Ori := TFileStream.Create(FileName, fmOpenRead);
Tmp := TMemoryStream.Create;
Tmp.CopyFrom(mssr_stream, StartPos);
//Tmp从Ori拷贝数据,但在StartPos与EndPos之间不拷,因此形同删除了一段数据
mssr_stream.Seek(EndPos,soFromBeginning);
Tmp.CopyFrom(mssr_stream, mssr_stream.Size-EndPos);
Tmp.SaveToStream(mssr_stream); //在此设置输出文件名
finally
FreeAndNil(Tmp);
end;
end;
procedure tjzck_form.DStreamData(FileName:String; StartPos,EndPos: Integer);
var
Buffer: array[0..10239] of Byte; //开辟1M缓存
ReadCount, Pos1, Pos2: Integer;
begin
try
Pos1 := StartPos;
Pos2 := EndPos;
repeat
mssr_stream.Seek(Pos2,soFromBeginning);
Pos2 := Pos2 + 10240;
ReadCount := mssr_stream.Read(Buffer, 10240);
if ReadCount > 0 then
begin
mssr_stream.Seek(Pos1, soFromBeginning);
mssr_stream.Write(Buffer, 10240);
Pos1 := Pos1 + 10240;
end;
until ReadCount <= 0;
mssr_stream.Seek(-(StartPos-EndPos), soFromEnd);
SetEndOfFile(mssr_stream);
finally
mssr_stream.Free;
end;
end;
执行后变成拷贝了一大堆乱码,。非常多
SetEndOfFile(mssr_stream.Handle);
还是一大堆乱码。谢谢
mssr_stream.Write(Buffer, 10240);改为:
mssr_stream.Write(Buffer, ReadCount);SetEndOfFile(mssr_stream)改为SetEndOfFile(mssr_stream.Handle);
再看看!嘻嘻,信手写不行,哎
Pos1 := Pos1 + ReadCount;没你那个流,没办法测试,真麻烦,再看看!