1

在 Delphi 2007 中,我如何制作一个程序来读取第一个文件,然后关闭它以读取第二个文件,依此类推,直到最后一个文件?

4

3 回答 3

4

您是否尝试读取目录中的每个文件?试试这门课。这不是我的原始代码,但我已经对其进行了一些修改和定制。它会为您提供与您在可以传递给 TFilestream 的字符串列表中设置的条件相匹配的所有文件名。

unit findfile;

interface

uses
  Classes;

type
   TFileAttrKind = (ffaReadOnly, ffaHidden, ffaSysFile, ffaDirectory, ffaArchive, ffaAnyFile);
   TFileAttr = set of TFileAttrKind;

   TFindFile = class(TObject)
   private
      s: TStringList;

      fSubFolder : boolean;
      fAttr: TFileAttr;
      FPath : string;
      FBasePath: string;
      fFileMask : string;
      FDepth: integer;

      procedure SetPath(Value: string);
      procedure FileSearch(const inPath : string);
      function cull(value: string): string;
   public
      constructor Create(path: string);
      destructor Destroy; override;

      function SearchForFiles: TStringList;

      property FileAttr: TFileAttr read fAttr write fAttr;
      property InSubFolders : boolean read fSubFolder write fSubFolder;
      property Path : string read fPath write SetPath;
      property FileMask : string read fFileMask write fFileMask ;
   end;

implementation

{$WARN SYMBOL_PLATFORM OFF}
{$WARN UNIT_PLATFORM OFF}
uses
   Windows, SysUtils, FileCtrl;

constructor TFindFile.Create(path: string);
begin
   inherited Create;
   FPath := path;
   FBasePath := path;
   FileMask := '*.*';
   FileAttr := [ffaReadOnly, ffaDirectory, ffaArchive];
   s := TStringList.Create;
   FDepth := -1;
end;

procedure TFindFile.SetPath(Value: string);
begin
   if fPath <> Value then
   begin
      if (Value <> '') and (DirectoryExists(Value)) then
         fPath := IncludeTrailingPathDelimiter(Value);
   end;
end;

function TFindFile.SearchForFiles: TStringList;
begin
   s.Clear;
   try
      FileSearch(Path);
   finally
      Result := s;
   end;
end;

function TFindFile.cull(value: string): string;
begin
   result := StringReplace(value, FBasePath, '', []);
end;

destructor TFindFile.Destroy;
begin
   s.Free;
   inherited Destroy;
end;

procedure TFindFile.FileSearch(const InPath : string);
var Rec  : TSearchRec;
    Attr : integer;
begin
   inc(FDepth);
   try
      Attr := 0;
      if ffaReadOnly in FileAttr then
         Attr := Attr + faReadOnly;
      if ffaHidden in FileAttr then
         Attr := Attr + faHidden;
      if ffaSysFile in FileAttr then
         Attr := Attr + faSysFile;
      if ffaDirectory in FileAttr then
         Attr := Attr + faDirectory;
      if ffaArchive in FileAttr then
         Attr := Attr + faArchive;
      if ffaAnyFile in FileAttr then
         Attr := Attr + faAnyFile;

      if SysUtils.FindFirst(inPath + FileMask, Attr, Rec) = 0 then
         try
            repeat
               if (Rec.Name = '.') or (Rec.Name = '..') then
                  Continue;
               s.Add(cull(inPath) + Rec.Name);
            until SysUtils.FindNext(Rec) <> 0;
         finally
            SysUtils.FindClose(Rec);
         end;

      If not InSubFolders then
         Exit;

      if SysUtils.FindFirst(inPath + '*.*', faDirectory, Rec) = 0 then
         try
            repeat
               if ((Rec.Attr and faDirectory) <> 0)  and (Rec.Name <> '.') and (Rec.Name <> '..') then
               begin
                  FileSearch(IncludeTrailingPathDelimiter(inPath + Rec.Name));
               end;
            until SysUtils.FindNext(Rec) <> 0;
         finally
            SysUtils.FindClose(Rec);
         end;
   finally
      dec(FDepth);
   end;
end;

end.
于 2009-05-02T14:01:11.987 回答
1

如果你想重复一个动作,那么你想要的就是一个循环。Delphi 带有三个用于循环的保留字:forrepeatwhile。所有都记录在帮助文件中;我认为最重要的主题叫做结构化陈述。你会很好地阅读它们。

for当您已经拥有要处理的事物的数组或列表时,传统的循环是最合适的。在您的情况下,可能是文件名列表。你可以这样写循环:

for i := 0 to High(FileNames) do begin ... end;

或这个:

for i := 0 to Pred(FileNames.Count) do begin ... end;

然后您将FileNames[i]在循环中引用以获取当前迭代的文件名。for当包含您的文件名的事物具有可用的枚举器或迭代器时,您还可以使用一种新型循环。然后你会这样写循环:

for name in FileNames do begin ... end;

Whilerepeat当您在循环开始之前不一定知道您需要运行代码多少次时,就会使用和循环。您可以将它与FindFirstFindNextDelphi 函数结合使用。例如:

if FindFirst('*.txt', faAnyFile, SearchResult) = 0 then try
  repeat
    // Do something with SearchResult.Name
  until FindNext(SearchResult) <> 0;
finally
  SysUtils.FindClose(SearchResult);
end;
于 2009-05-03T15:16:44.463 回答
1

DIFileFinder可能是您想要的。

于 2009-05-02T14:58:31.270 回答