Search the files in drectory with pattern matching using C#

82 views Asked by At

I am working on migration of legacy Windown form app wrriten in vb.net to .net core api (C#).

There is as an code statement written in VB.net to search the file in directory

Function HasDoc(ByVal branch As String, ByVal sender As String, ByVal appName As String) As Boolean
     Dim strPath = "T:\" + appName + branch + "\" + sender + "\_" + branch + "_*.*"
     dim ls_files = Dir(strPath, FileAttribute.Archive)
     dim bolExist as Boolean
     If ls_files = Nothing Then
        bolExist = False
     Else
        bolExist = True
     End If
     return bolExist 
End Function 

I am using c# statement to replicate below line of code

dim ls_files = Dir(strPath, FileAttribute.Archive)

C# Code

    public bool HasDoc(string appName, string branch, string sender)
    {
       
        var filesPath = "T:\\" + appName + branch + @"\" + sender;
        var strPatt = "_" + branch + "_*.*";
       
        if (System.IO.Directory.Exists(filesPath))
             return Directory.EnumerateFiles(filesPath, strPatt).Any();

        return false;
                    
    }

Code I written in C#, performance is very slow and also I am not sure how to use FileAttribute.Archive? where legacy code performance comparatively faster than mine, the file location where above code searching the files contain millions of documents.

Please suggest what I can use to replicate the same Vb.net code behaviour

1

There are 1 answers

2
Panagiotis Kanavos On

The call Dir(strPath, FileAttribute.Archive) searches for a file that matches the pattern and has the Archive attribute set. Dir is actually a VB6 function that remained in VB.NET only to ease migration to the new environment. Underneath it uses the same classes that C# does, eg DirectoryInfo.GetFileSystemInfos. It's not possible to filter by attribute, so the implementation loops over all the files and checks their attributes.

The Microsoft.VisualBasic.* convenience libraries allow you to use the same functions as VB.NET, eg Dir but these are rarely used nowadays.

You can use the DirectoryInfo class in C# directly. GetFileSystemInfos returns an array with objects representing all contents of a folder, both directories and files. You can use EnumerateFileSystemInfos instead to return an IEnumerable<> that only returns items as you read them. Since you only want files, you can use EnumerateFiles instead of EnumerateFileSystemInfos. This returns an IEnumerable<FileInfo> instead of a string[], which allows you to check a file's attributes.

For example:

var dir= new DirectoryInfo(dirPath);
var pattern=$"_{branch}_*.*";

var files=dir.EnumerateFiles(pattern);
var found=files.Any(file=>file.Attributes.HasFlag(FileAttribute.Archive));

You can swap EnumerateFiles with GetFiles or even GetFileSystemInfos to see if this affects performance.

All these functions accept an EnumerationOptions parameter that can be used to specify recursion depth, buffer sizes etc.

var options=new EnumerationOptions {
    BufferSize = 16384
};
var files=dir.EnumerateFiles(pattern,options );