0

how can I resolve the wildcard * char if is used in source path.

Input parameter explained in below example :

For example, C:\Owners*\App*\Temp* resolves as:

C:\Owners\User1\App\Local\Temp*

C:\Owners\User1\App\LocalDir\Temp*

C:\Owners\User1\App\Roam\Temp*

C:\Owners\User2\App\Local\Temp*

C:\Owners\User2\App\LocalDir\Temp*

C:\Users\User2\App\Roaming\Temp*

File delete and directory delete can be done but I am unable to resolve the path when it contains wildcard char as *.

1
  • Filename wildcard is ok. But what is wildcard in path name? You cannot change directory with * in path. Commented May 29, 2023 at 8:37

1 Answer 1

0

Do you want to process a path that contains wildcards and delete found folders/files? As far as I know, there are currently no methods that allow wildcards to be used in any part of the path. So I wrote my method:

/// <summary> /// Parse path that may contain wildcards /// </summary> /// <param name="pathWithWildcards">The pattern by which we are looking for files/folders</param> /// <param name="isFolder">Looking for folders or files?</param> /// <returns>List of paths that match the specified pattern</returns> public static List<string> ParsePath(string pathWithWildcards, bool isFolder = false) { if (string.IsNullOrEmpty(pathWithWildcards)) return new List<string>(0); if (!pathWithWildcards.Any(x => x == '*' || x == '?')) return new List<string> { pathWithWildcards }; if (!pathWithWildcards.Contains(':')) { string[] pathParts = pathWithWildcards.Split('\\'); pathParts[0] = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, pathParts[0]).TrimEnd('\\'); pathWithWildcards = string.Join("\\", pathParts); } List<string> paths = new List<string>(); List<string> patterns = new List<string> { pathWithWildcards }; while (patterns.Count > 0) { string[] pathParts = patterns[0].Split('\\'); for (int i = 0; i < pathParts.Length; i++) { if (!pathParts[i].Any(x => x == '*' || x == '?')) continue; string firstPart = string.Join("\\", pathParts.Take(i)) + "\\"; string lastPart = pathParts.Length > i + 1 ? string.Join("\\", pathParts.Skip(i + 1)) : string.Empty; if (!Directory.Exists(firstPart)) { patterns.RemoveAt(0); break; } bool isFinalAndFile = lastPart.Length == 0 && !isFolder; string[] search = isFinalAndFile ? Directory.GetFiles(firstPart, pathParts[i]) : Directory.GetDirectories(firstPart, pathParts[i]); if (lastPart.Length > 0) search = search.Select(x => Path.Combine(x, lastPart)).ToArray(); IEnumerable<string> withPattern = search.Where(x => x.Any(y => y == '*' || y == '?')); patterns.AddRange(withPattern); paths.AddRange(search.Except(withPattern).Where(x => isFinalAndFile ? File.Exists(x) : Directory.Exists(x))); patterns.RemoveAt(0); break; } } return paths; } 

Usage example:

Stopwatch sw = new Stopwatch(); string path1 = "C:\\Users\\*\\AppData\\*\\Ad?be\\Color"; sw.Start(); List<string> test1 = ParsePath(path1, true); Console.WriteLine($"Found: {test1.Count} folder(s)\nElapsed time: {sw.ElapsedMilliseconds} ms\nList:"); test1.ForEach(f => Console.WriteLine(f)); string path2 = "C:\\Users\\*\\AppData\\*\\Ad?be\\Color\\ACE*.lst"; sw.Restart(); List<string> test2 = ParsePath(path2); Console.WriteLine($"Found: {test2.Count} file(s)\nElapsed time: {sw.ElapsedMilliseconds} ms\nList:"); test2.ForEach(f => Console.WriteLine(f)); string path3 = "*\\test (*).txt"; sw.Restart(); List<string> test3 = ParsePath(path3); Console.WriteLine($"Found: {test3.Count} file(s)\nElapsed time: {sw.ElapsedMilliseconds} ms\n"); // Output: // Found: 2 folder(s) // Elapsed time: 13 ms // List: // C:\Users\Andrew\AppData\Local\Adobe\Color // C:\Users\Andrew\AppData\Roaming\Adobe\Color // Found: 2 file(s) // Elapsed time: 2 ms // List: // C:\Users\Andrew\AppData\Local\Adobe\Color\ACECache11.lst // C:\Users\Andrew\AppData\Roaming\Adobe\Color\ACEConfigCache2.lst // Found: 2000 file(s) // Elapsed time: 105 ms 

Found folders/files can be deleted immediately, but I advise you to do this only if you are completely sure of your pattern. Otherwise, you may accidentally delete important data

ParsePath("Test folder\\*\\*.txt").ForEach(f => File.Delete(f)); ParsePath("Test folder\\*", true).ForEach(f => Directory.Delete(f)); 
Sign up to request clarification or add additional context in comments.

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.