Visit our Sponsor   Visit our Sponsor
delphi3000.com - the free delphi knowledge platform
delphi3000.com - the free delphi knowledge platform
460 Users Online NOW
Have a look at your member-status

connecting people's knowledge


  - Recent ArticlesRSS feed for Recent Articles on delphi3000.com
  - List of All Articles
  - Top Viewed Articles
  - Articles (+Attachem.)
  - Articles Of Interest
  - Categories
  - Top Uploader
  - Search
  - Index

  - My Home
  - Submit an Article
  - My Articles
  - My Personal Data
  - My Bookmarks
  - Activities
  - Login/Logout

  - Sign Up
  - Why Sign Up
  - Newsletter

  - Press
  - Advertise

  - Contact
  - Feedback





Community
Borland
ClubeDelphi
Dr. Bob
UK-BUG
Delphi Meetings
Planeta Delphi







Startblatt.de






Share this article with friendsShare this article with friends
Rate this articleRate this article - to keep the quality of delphi3000.com !
Comment this article or read through previous comments (3)


Looking for files recursively in a directory or the hard diskFormat this article printer-friendly!Bookmark function is only available for registered users!
Getting the names and attributes of files in a directory and all its subdirectories
Product:
Delphi 3.x (or higher)
Category:
Files Operation
Skill Level:
Scoring:
Last Update:
07/11/2001
Search Keys:
delphi delphi3000 article borland vcl code-snippet FindFile look-for search get name names file filename directory subdirectories recurse recursion recursively folder FindFirst FindNext FindClose TSearchRec faArchive faReadOnly faHidden faSysFile faDirectory faVolumeID
Times Scored:
16
Visits:
8803
Uploader: Ernesto De Spirito
Company: Latium Software
Reference: http://www.latiumsoftware.com/en/
 
Question/Problem/Abstract:
How can search a directory recursively?
Answer:



The following function receives as parameters a file specification
(like for example 'C:\My Documents\*.xls' or 'C:\*' if you want to
search the entire hard disk) and optionally a set of attributes
(exactly as Delphi's FindFirst function), and it returs a StringList
with the full pathnames of the found files. You should free the
StringList after using it.


  interface

  function FindFile(const filespec: TFileName; attributes: integer
     = faReadOnly Or faHidden Or faSysFile Or faArchive): TStringList;

  implementation

  function FindFile(const filespec: TFileName;
                    attributes: integer): TStringList;
  var
    spec: string;
    list: TStringList;

  procedure RFindFile(const folder: TFileName);
  var
    SearchRec: TSearchRec;
  begin
    // Locate all matching files in the current
    // folder and add their names to the list
    if FindFirst(folder + spec, attributes, SearchRec)=0 then begin
      try
        repeat
          if (SearchRec.Attr and faDirectory = 0) or
             (SearchRec.Name<>'.') and (SearchRec.Name<>'..') then
            list.Add(folder + SearchRec.Name);
        until FindNext(SearchRec) <> 0;
      except
        FindClose(SearchRec);
        raise;
      end;
      FindClose(SearchRec);
    end;
    // Now search the subfolders
    if FindFirst(folder + '*', attributes
        Or faDirectory, SearchRec) = 0 then
    begin
      try
        repeat
          if ((SearchRec.Attr and faDirectory) <> 0) and
             (SearchRec.Name<>'.') and (SearchRec.Name<>'..') then
            RFindFile(folder + SearchRec.Name + '\');
        until FindNext(SearchRec) <> 0;
      except
        FindClose(SearchRec);
        raise;
      end;
      FindClose(SearchRec);
    end;
  end; // procedure RFindFile inside of FindFile

  begin // function FindFile
    list := TStringList.Create;
    try
      spec := ExtractFileName(filespec);
      RFindFile(ExtractFilePath(filespec));
      Result := list;
    except
      list.Free;
      raise;
    end;
  end;


Sample call
-----------

You can try this function placing a ListBox and a button on a form
and adding this code to the OnClick event of the button:

  procedure TForm1.Button1Click(Sender: TObject);
  var
    list: TStringList;
  begin
    list := FindFile('C:\Delphi\*.pas');
    ListBox1.Items.Assign(list);
    list.Free;
  end;





Please rate this article!
Skill level:
BeginnerExpert

Useful:
No!Very!

Overall rating:
PoorExcellent



Comments to this article
Write a new comment
Thanks!
    Peter Tickler (Oct 2 2003 11:17AM)

A really useful piece of code. Thanks a lot.
Respond

Great Code
    Vimil Saju (Mar 11 2001 7:55AM)

Your code is great.

I thought if there was a way to create a function that does not recursively call itself to list all the files in the harddisk, so that there might be some improvement in speed, other than making the function more complex there were no speed improvements. Here is the code of the function any way.
--------------------------------------------------------------------------------------------------------
type
  PRecInfo=^TRecInfo;
  Trecinfo=record
   prev:PRecInfo;
   fpathname:string;
   srchrec:Tsearchrec;
  end;

function TForm1.RecurseDirectory1(fname:string):tstringlist;
var
f1,f2:Tsearchrec;
p1,tmp:PRecInfo;
fwc:string;
fpath:string;
fbroke1,fbroke2:boolean;
begin
result:=tstringlist.create;
fpath:=extractfilepath(fname);
fwc:=extractfilename(fname);
new(p1);
p1.fpathname:=fpath;
p1.prev:=nil;
fbroke1:=false;
fbroke2:=false;
while(p1<>nil) do
  begin
   if (fbroke1=false) then
    if (fbroke2=false) then
     begin
      if (findfirst(fpath+'*',faAnyfile,f1)<>0) then
       break;
     end

                                                                   ---Contd in next Comment

Respond

RE: Great Code
Vimil Saju (Mar 11 2001 7:57AM)

-------Contd From Previous Comment
--------------------------------------------------------------------------------------------------------
    else if (findnext(f1)<>0) then
     begin
      repeat
       findclose(f1);
       if (p1=nil) then
        break;
       fpath:=p1.fpathname;
       f1:=p1.srchrec;
       tmp:=p1.prev;
       dispose(p1);
       p1:=tmp;
      until (findnext(f1)=0);
      if (p1=nil) then
       break;
     end;
   if((f1.Name<>'.') and (f1.name<>'..') and ((f1.Attr and fadirectory)=fadirectory)) then
    begin
     fbroke1:=false;
     new(tmp);
     with tmp^ do
      begin
       fpathname:=fpath;
       srchrec.Time:=f1.time;
       srchrec.Size:=f1.size;
       srchrec.Attr:=f1.attr;
       srchrec.Name:=f1.name;
       srchrec.ExcludeAttr:=f1.excludeattr;
       srchrec.FindHandle:=f1.findhandle;
       srchrec.FindData:=f1.FindData;
      end;
     tmp.prev:=p1;
     p1:=tmp;
     fpath:=p1.fpathname+f1.name+'\';
     if findfirst(fpath+fwc,faAnyfile,f2)=0 then
      begin
       result.add(fpath+f2.Name);
       while(findnext(f2)=0) do
        result.add(fpath+f2.Name);
       findclose(f2);
      end;
     fbroke2:=false;
    end
   else
    begin
     if (findnext(f1)<>0) then
      begin
       findclose(f1);
       fpath:=p1.fpathname;
       f1:=p1.srchrec;
       fbroke1:=false;
       fbroke2:=true;
       tmp:=p1.prev;
       dispose(p1);
       p1:=tmp;
      end
     else
      begin
       fbroke1:=true;
       fbroke2:=false;
      end;
    end;
  end;
fpath:=extractfilepath(fname);
if findfirst(fname,faAnyfile,f1)=0 then
  begin
   result.add(fpath+f2.Name);
   while(findnext(f1)=0) do
    result.add(fpath+f2.Name);
   findclose(f1);
  end;
end;
--------------------------------------------------------------------------------------------------------
Regards
Vimil
Respond














 
Sign up to consume product discounts for Bronze memberships !

read more


  Visit our Sponsor

 

  Community Ad of
D. Wischnewski
 
   














 







     
  Copyright © 2000 - 2007 delphi3000.com - All rights reserved. Terms of use. || Privacy
delphi3000.com is a service by bluestep.com IT-Services GmbH (Vienna)