检查数组中的目录名称

Check for name of a directory from an array

提问人:anonfoxer 提问时间:8/17/2021 最后编辑:Uwe Keimanonfoxer 更新时间:8/17/2021 访问量:224

问:

我正在开发一个程序,该程序应该扫描特定目录,查找其中具有特定名称的任何目录,如果找到它们,请告诉用户。

目前,我加载其搜索名称的方式如下:

static string path = Path.Combine(Directory.GetCurrentDirectory(), @"database.txt");
static string[] database = File.ReadAllLines(datapath);

我将其用作在查看特定目录时要查找的名称数组。我正在使用 foreach 方法这样做。

System.IO.DirectoryInfo di = new DirectoryInfo("C:\ExampleDirectory");
        foreach (DirectoryInfo dir in di.GetDirectories())
        {

        }

有没有办法查看文件“database.txt”中的任何名称是否与在“C:\ExampleDirectory”中找到的任何目录名称匹配?

我能想到的唯一方法是:

System.IO.DirectoryInfo di = new DirectoryInfo(versionspath);
        foreach (DirectoryInfo dir in di.GetDirectories())
        {
            if(dir.Name == //Something...) {
            Console.WriteLine("Match found!");
            break;}
        }

但这显然是行不通的,我想不出任何其他方法可以做到这一点。任何帮助将不胜感激!

C# 数组 目录 匹配

评论

0赞 41686d6564 8/17/2021
if (database.Contains(dir.Name)) { ... }

答:

0赞 faso 8/17/2021 #1

可以使用 LINQ 来执行此操作

var allDirectoryNames = di.GetDirectories().Select(d => d.Name);
var matches = allDirectoryNames.Intersect(database);

if (matches.Any())
    Console.WriteLine("Matches found!");

在第一行中,我们获取所有目录名称,然后我们使用该方法查看哪些目录名称同时存在于 和Intersect()allDirectoryNamesdatabase

1赞 Oliver 8/17/2021 #2

像往常一样,LINQ 是必经之路。每当您必须在两个列表之间以及两个包含不同类型的列表之间查找匹配或不匹配时,都必须使用 或 。.Join().GroupJoin()

如果您需要找到 1:1 关系和任何类型的 1-to 关系(1:0、1:many 或 1:1),它就会发挥作用。.Join().GroupJoin()

因此,如果您需要与您的列表匹配的目录,这对操作员来说听起来是一项工作:.Join()

public static void Main(string[] args)
{
    // Where ever this comes normally from.
    string[] database = new[] { "fOo", "bAr" };
    string startDirectory = @"D:\baseFolder";

    // A method that returns an IEnumerable<string>
    // Using maybe a recursive approach to get all directories and/or files
    var candidates = LoadCandidates(startDirectory);

    var matches = database.Join(
        candidates,
        // Simply pick the database entry as is.
        dbEntry => dbEntry,
        // Only take the last portion of the given path.
        fullPath => Path.GetFileName(fullPath),
        // Return only the full path from the given matching pair.
        (dbEntry, fullPath) => fullPath,
        // Ignore case on comparison.
        StringComparer.OrdinalIgnoreCase);

    foreach (var match in matches)
    {
        // Shows "D:\baseFolder\foo"
        Console.WriteLine(match);
    }

    Console.ReadKey();
}

private static IEnumerable<string> LoadCandidates(string baseFolder)
{
    return new[] { @"D:\baseFolder\foo", @"D:\basefolder\baz" };
    //return Directory.EnumerateDirectories(baseFolder, "*", SearchOption.AllDirectories);
}
1赞 Steeeve 8/17/2021 #3

根据你在 stackoverflow 上的其他问题,我认为你的问题是家庭作业,或者你是一个充满激情的爱好程序员,对吗?因此,我将尝试在这里解释原理,继续您几乎完整的解决方案。
你在这里需要一个嵌套的循环,一个循环中的循环。在外部循环中,遍历目录。你已经得到了这个。对于每个目录,您需要遍历名称,以查看其中是否有任何项目与目录的名称匹配:
database

System.IO.DirectoryInfo di = new DirectoryInfo(versionspath);
foreach (DirectoryInfo dir in di.GetDirectories())
{
    foreach (string name in database)
    {        
        if (dir.Name == name)
        {
            Console.WriteLine("Match found!");
            break;
        }
    }
}

根据您的目标,您可能希望在第一个匹配的目录处退出。上面的示例代码没有。单个语句仅退出内部循环,而不退出外部循环。因此,它继续检查下一个目录。试着自己弄清楚如何在第一场比赛中停止(通过退出外循环)。break;

评论

0赞 anonfoxer 8/18/2021
我在堆栈上得到的最佳答案哈哈。是的,热情的业余爱好者(希望只要我能积聚动力,就成为一名学生,而 COVID 不会杀死我和我所爱的每个人。我想我有一个解决方案,可以在第一场比赛中爆发(这是我理想情况下应该做的。 想到这是尽早做到这一点的最佳方式,而不是通过所有比赛),虽然它可能不优雅,但希望它能奏效。非常感谢 <3
1赞 Steeeve 8/18/2021
我很高兴它有所帮助。祝您编码愉快!;)