访问路径'd:\ $ RECYCLE.BIN\S-1-5-21-494745725-312220573-749543506-41600'被拒绝

San*_*joo 5 c#

我是C#的新手.我有一个文本框,我输入要搜索的文件和"搜索"按钮.在搜索时钟我希望它填充文件夹中的文件,但我得到上述错误.以下是我的代码:

string[] directories = Directory.GetDirectories(@"d:\",
                                              "*",
                                              SearchOption.AllDirectories);
string file = textBox1.Text;
DataGrid dg = new DataGrid();

{
    var files = new List<string>();
     foreach (DriveInfo d in DriveInfo.GetDrives().Where(x => x.IsReady))
        {
        try
        {
            files.AddRange(Directory.GetFiles(d.RootDirectory.FullName,  file , SearchOption.AllDirectories));
        }
        catch(Exception ex)
        {
            MessageBox.Show("the  exception is " + ex.ToString());
            //Logger.Log(e.Message); // Log it and move on
        }
}
Run Code Online (Sandbox Code Playgroud)

请帮我解决一下.谢谢

Ian*_*Ian 2

搜索可能包含无法访问子文件夹的文件夹时最重要的规则是:

不使用!SearchOption.AllDirectories

相反SearchOption.TopDirectoryOnly,结合递归搜索所有可访问的目录。

使用SearchOption.AllDirectories,即使在处理任何文件/目录之前,一次访问冲突也会中断整个循环。但如果您使用SearchOption.TopDirectoryOnly,您只会跳过无法访问的内容。

有更困难的方法来使用Directory.GetAccessControl()每个子目录检查来查看您是否可以事先访问目录(尽管这个选项相当困难 - 我真的不推荐这样做,除非您确切地知道访问系统是如何工作的)。

对于递归搜索,我实现了以下代码供我自己使用:

public static List<string> GetAllAccessibleDirectories(string path, string searchPattern) {
    List<string> dirPathList = new List<string>();
    try {
        List<string> childDirPathList = Directory.GetDirectories(path, searchPattern, SearchOption.TopDirectoryOnly).ToList(); //use TopDirectoryOnly
        if (childDirPathList == null || childDirPathList.Count <= 0) //this directory has no child
            return null;
        foreach (string childDirPath in childDirPathList) { //foreach child directory, do recursive search
            dirPathList.Add(childDirPath); //add the path
            List<string> grandChildDirPath = GetAllAccessibleDirectories(childDirPath, searchPattern);
            if (grandChildDirPath != null && grandChildDirPath.Count > 0) //this child directory has children and nothing has gone wrong
                dirPathList.AddRange(grandChildDirPath.ToArray()); //add the grandchildren to the list
        }
        return dirPathList; //return the whole list found at this level
    } catch {
        return null; //something has gone wrong, return null
    }
}
Run Code Online (Sandbox Code Playgroud)

这就是你所说的

List<string> accessibleDirs = GetAllAccessibleDirectories(myrootpath, "*");
Run Code Online (Sandbox Code Playgroud)

然后,您只需在所有可访问的目录中搜索/添加文件即可。

注意:这个问题虽然很经典。我相信还有其他一些更好的解决方案。

如果在获取所有可访问目录后您特别想要避免某些目录,您还可以List使用目录名称的一部分作为关键字(即Recycle.Bins)通过 LINQ 过滤结果。