【发布时间】:2012-05-30 20:07:46
【问题描述】:
我正在尝试测量FILE_FLAG_WRITE_THROUGH 和FILE_FLAG_NO_BUFFERING 对文件中一系列写入的影响,正如another question 中的请求。但是我发现我无法写入带有FILE_FLAG_NO_BUFFERING 设置的文件。
当我使用它时,Delphi 返回EWriteError 和消息stream read error。
使用的代码如下:
procedure TForm1.btn1Click(Sender: TObject);
var
fsFSArquivoAAC: TFileStream;
L, lastErr: Cardinal;
R: WideString;
hn: THandle;
begin
hn := Windows.CreateFile( PChar('TesteAAC.AAC2'),
GENERIC_READ or GENERIC_WRITE,
FILE_SHARE_READ or FILE_SHARE_WRITE, nil, CREATE_ALWAYS,
FILE_ATTRIBUTE_NORMAL or FILE_FLAG_WRITE_THROUGH or FILE_FLAG_NO_BUFFERING, 0);
lastErr := GetLastError();
if (lastErr <> ERROR_SUCCESS) then
begin
if (lastErr <> ERROR_ALREADY_EXISTS ) then
begin
MessageDlg('Whoops, something went wrong with CreateFile!',
mtError, [mbOK], 0);
end
else
begin
SetLastError(ERROR_SUCCESS);
end;
end;
fsFSArquivoAAC := TFileStream.Create( hn );
try
R := 'BatatinhaquandoNasceEspalharamapelochao';
// write WideString
L := Length(R);
fsFSArquivoAAC.WriteBuffer(L, SizeOf(integer));
if L > 0 then
fsFSArquivoAAC.WriteBuffer(R[1], L * SizeOf(WideChar));
finally
fsFSArquivoAAC.Free;
end;
如果您评论 FILE_FLAG_NO_BUFFERING 代码有效。为什么?
【问题讨论】:
-
请注意,您没有正确处理错误。您只是在创建一个异常对象,然后将其丢弃。您打算使用
raise,但更好的是,请改用RaiseLastOSError。但是由于在调用CreateFile和检查故障之间可能会调用许多操作系统函数,因此最好将文件句柄存储在单独的变量中,立即检查,然后然后将它传递给构造函数。记住try-finally,这样你就可以释放流并关闭文件句柄以防出现异常(如EWriteError)。 -
@RobKennedy 感谢您的编辑。你说的对。该代码根本没有进行异常处理。另外,我不想让它复杂化,因为简单的代码只是显示了错误。我希望现在好多了。仍然是同样的错误想法。