2011-02-13 69 views
10

时,访问路径被拒绝我正在运行下面的代码并在下面得到例外。我是否试图把这个函数放在try catch中,还是有其他方法来递归地获取所有的目录? 我可以写我自己的递归函数来获取文件和目录。但我想知道是否有更好的方法。当使用Directory.GetFiles(...)

// get all files in folder and sub-folders 
var d = Directory.GetFiles(@"C:\", "*", SearchOption.AllDirectories); 

// get all sub-directories 
var dirs = Directory.GetDirectories(@"C:\", "*", SearchOption.AllDirectories); 

“访问路径'C:\ Documents and Settings \'被拒绝。”

+0

可能重复(http://stackoverflow.com/questions/172544/ignore-folders-files-when-directory-getfiles-is -denied-access) – Ani 2011-02-13 19:44:23

+0

@Ani谢谢!为了指出。但是我没有找到足够好的答案。我想获得一个替代解决方案。 – 2011-02-13 20:10:17

回答

30

如果你想在失败后继续下一个文件夹,那么是的;你必须自己做。我会推荐Stack<T>(深度优先)或Queue<T>(繁殖第一),而不是递归,和迭代块(yield return);那么你可以避免堆栈溢出和内存使用问题。

例子:

public static IEnumerable<string> GetFiles(string root, string searchPattern) 
    { 
     Stack<string> pending = new Stack<string>(); 
     pending.Push(root); 
     while (pending.Count != 0) 
     { 
      var path = pending.Pop(); 
      string[] next = null; 
      try 
      { 
       next = Directory.GetFiles(path, searchPattern);      
      } 
      catch { } 
      if(next != null && next.Length != 0) 
       foreach (var file in next) yield return file; 
      try 
      { 
       next = Directory.GetDirectories(path); 
       foreach (var subdir in next) pending.Push(subdir); 
      } 
      catch { } 
     } 
    } 
+1

+1 @Marc感谢您提供替代解决方案。现在你给了我一个递归的替代方案,请你提供一个例子吗? – 2011-02-13 20:07:59

2

好了,你要么避免的目录,而您没有权限,或者你不却对正常时访问被拒绝响应。

如果您选择第一个选项,则需要确保知道它们是什么目录以及线程身份的权限不会更改。这很棘手,容易出错;我不会推荐它用于生产质量系统。

第二个选项看起来更合适。使用try/catch块并跳过任何“禁止”目录。

7

您可以设置程序,以便您只能以管理员身份运行。

Visual Studio中

Right click on the Project -> Properties -> Security -> Enable ClickOnce Security Settings 

在你点击它,文件将在该项目的属性,可以创建文件夹,名为app.manifest一旦被创建,您可以取消选中Enable ClickOnce Security Settings选项

打开该文件,并改变这一行:

<requestedExecutionLevel level="asInvoker" uiAccess="false" /> 

到:

<requestedExecutionLevel level="requireAdministrator" uiAccess="false" /> 

这将使该程序需要管理员权限,这将保证您可以访问该文件夹。

0

我知道这个问题有点旧,但我今天有同样的问题,我发现下面的文章详细解释了'文件夹递归'解决方案。

的制品确认GetDirectories()方法的缺陷...:

不幸的是,此[使用GetDirectories()方法]有问题。其中的关键是您尝试读取的文件夹中的某些文件可能被配置,以致当前用户可能无法访问它们。该方法抛出 UnauthorizedAccessException,而不是将文件夹忽略为 。但是,我们可以通过创建我们自己的递归文件夹搜索代码来绕过这个问题 。

...然后详细介绍了解决方案:

http://www.blackwasp.co.uk/FolderRecursion.aspx

0

前面已经指出,你需要自己做,所以我想我会分享我的解决方案,避免了一路上收藏。应该指出的是,这将忽略所有错误,而不仅仅是AccessDenied。要改变这种情况,你可以使catch块更具体。的[忽略文件夹/文件时Directory.GetFiles()被拒绝访问]

IEnumerable<string> GetFiles(string folder, string filter, bool recursive) 
    { 
     string [] found = null; 
     try 
     { 
      found = Directory.GetFiles(folder, filter); 
     } 
     catch { } 
     if (found!=null) 
      foreach (var x in found) 
       yield return x; 
     if (recursive) 
     { 
      found = null; 
      try 
      { 
       found = Directory.GetDirectories(folder); 
      } 
      catch { } 
      if (found != null) 
       foreach (var x in found) 
        foreach (var y in GetFiles(x, filter, recursive)) 
         yield return y; 
     } 
    }