Delphi, удали папку с контентом - PullRequest
9 голосов
/ 19 апреля 2011

когда у меня есть подпапка в папке - этот код не удаляет папки ... Есть ли ошибка?

procedure TForm.Remove(Dir: String);
var
  Result: TSearchRec; Found: Boolean;
begin
  Found := False;
  if FindFirst(Dir + '\*', faAnyFile, Result) = 0 then
    while not Found do begin
      if (Result.Attr and faDirectory = faDirectory) AND (Result.Name <> '.') AND (Result.Name <> '..') then Remove(Dir + '\' + Result.Name)
      else if (Result.Attr and faAnyFile <> faDirectory) then DeleteFile(Dir + '\' + Result.Name);
      Found := FindNext(Result) <> 0;
    end;
  FindClose(Result); RemoveDir(Dir);
end;

Ответы [ 5 ]

29 голосов
/ 19 апреля 2011

Самое простое, что нужно сделать, это позвонить TDirectory.Delete(Dir, True).

TDirectory находится в IOUtils, что является довольно недавним добавлением RTL.

Флаг True передается параметру Recursive, который означает, что содержимое каталогов удаляется до удаления каталога, что является важной частью удаления каталогов.


В комментарии вы сообщаете нам, что используете Delphi 7, и поэтому его нельзя использовать.

Ваш код выглядит в основном нормально. Тем не менее, вы не имеете в виду:

(Result.Attr and faAnyFile <> faDirectory)

Я думаю, вы имеете в виду:

(Result.Attr and faDirectory <> faDirectory)

Я бы, наверное, написал это следующим образом:

procedure TMyForm.Remove(const Dir: string);
var
  Result: TSearchRec;
begin
  if FindFirst(Dir + '\*', faAnyFile, Result) = 0 then
  begin
    Try
      repeat
        if (Result.Attr and faDirectory) = faDirectory then
        begin
          if (Result.Name <> '.') and (Result.Name <> '..') then
            Remove(Dir + '\' + Result.Name)
        end
        else if not DeleteFile(Dir + '\' + Result.Name) then
          RaiseLastOSError;
      until FindNext(Result) <> 0;
    Finally
      FindClose(Result);
    End;
  end;
  if not RemoveDir(Dir) then
    RaiseLastOSError;
end;
27 голосов
/ 19 апреля 2011

На вашем месте я бы просто попросил операционную систему удалить папку со всем ее содержимым. Сделайте это, написав (uses ShellAPI)

var
  ShOp: TSHFileOpStruct;
begin
  ShOp.Wnd := Self.Handle;
  ShOp.wFunc := FO_DELETE;
  ShOp.pFrom := PChar('C:\Users\Andreas Rejbrand\Desktop\Test\'#0);
  ShOp.pTo := nil;
  ShOp.fFlags := FOF_NO_UI;
  SHFileOperation(ShOp);

[Если вы делаете

  ShOp.fFlags := 0;

Вместо этого вы получите хороший диалог подтверждения. Если вы делаете

ShOp.fFlags := FOF_NOCONFIRMATION;

вы не получаете диалог подтверждения, но вы получаете индикатор выполнения, если операция длительная. Наконец, если вы добавите флаг FOF_ALLOWUNDO, вы переместите каталог в мусорную корзину вместо того, чтобы окончательно удалить его.

ShOp.fFlags := FOF_ALLOWUNDO;

Конечно, вы можете комбинировать флаги как хотите:

ShOp.fFlags := FOF_NOCONFIRMATION or FOF_ALLOWUNDO;

не будет отображать никаких подтверждений (кроме диалогового окна хода выполнения, поскольку вы не указали FOF_NO_UI), и каталог будет перемещен в мусорную корзину и не будет удален окончательно.]

9 голосов
/ 19 апреля 2011

В последний раз, когда мне нужно было удалить папку с содержимым, я использовал JCL :

uses JclFileUtils;

DeleteDirectory(DirToDelete, True);

Последний параметр указывает, должны ли файлы идти в корзину или нет,Это хороший бонус.

5 голосов
/ 20 апреля 2011

Для решения исходной проблемы - попробуйте это:

procedure TForm.Remove(const Dir: String);
var
  sDir: String;
  Rec: TSearchRec;
begin
  sDir := IncludeTrailingPathDelimiter(Dir);
  if FindFirst(sDir + '*.*', faAnyFile, Rec) = 0 then
  try
    repeat
      if (Rec.Attr and faDirectory) = faDirectory then
      begin
        if (Rec.Name <> '.') and (Rec.Name <> '..') then
          Remove(sDir + Rec.Name);
      end else
      begin
        DeleteFile(sDir + Rec.Name);
      end;
    until FindNext(Rec) <> 0;
  finally
    FindClose(Rec);
  end;
  RemoveDir(sDir);
end; 
3 голосов
/ 19 апреля 2011
uses DSiWin32;

DSiDeleteTree(folderName, false);

DSiWin32 - проект с открытым исходным кодом, имеющий лицензию «используйте как хотите».

...