问题
I want to check if a folder exists and if not then create it. But I don't know if the path supplied will even valid. When the path is not valid the following happens.
string path = "this is an invalid path";
if (!Directory.Exists(path))
Directory.CreateDirectory(path); //Exception thrown here
If you supply an invalid path, it will throw a DirectoryNotFoundException
exception.
How can I stop this exception from occurring? I don't want to use a try-catch. I want to detect that this exception will occur even before the exception happens.
回答1:
The explanation for the failure of your code is that the path is invalid. The documentation says:
DirectoryNotFoundException
The specified path is invalid (for example, it is on an unmapped drive).
Trying to predict in advance whether or not a directory can be created is a devil of a job. You'd need to account for security, OS name rules and limits, file system name rules and limits, and whether or not drives are mapped. And probably lots more concerns. I would not contemplate re-implementing what the system provides for free.
In any case, whilst you can call Directory.Exists
, you do still need to allow for an exception being thrown. If the file system changes between the call to Directory.Exists
and the subsequent call to Directory.CreateDirectory
, then an exception will be raised. For example, if another process creates the directory that you are trying to create. Granted, this is a rather unlikely event, but it's perfectly possible.
In summary, the best option, by a distance, is to catch the exception. As the well known saying goes, it's better to ask for forgiveness than to ask for permission.
回答2:
Use Directory.Exists method to check if a folder exists
if(Directory.Exists(path))
{
//Directory exists
}
else
{
// doesn't exist
}
Remember to include System.IO;
回答3:
Why don't you want to catch (specific) Exceptions? It is considered as a good practice... anyway, these are my solutions without try/catch:
solution:
string path = "C:\test"; if (!Directory.Exists(path) && path.IndexOfAny(Path.GetInvalidFileNameChars()) == -1) { Directory.CreateDirectory(path); }
solution:
string path = "C:\test"; var canCreate = true; foreach (var c in path.Where(Path.GetInvalidFileNameChars().Contains)) { canCreate = false; } if (canCreate && !Directory.Exists(path)) { Directory.CreateDirectory(path); }
solution:
if (path.Any(c => Path.GetInvalidFileNameChars().Contains(c)) && !Directory.Exists(path)) { Directory.CreateDirectory(path); }
Please, be aware that this code can still fail... e.g. think about SecurityExeption (do you have the credentionals to create a directory there?!?
Also be aware there is still a (little) chance that the directory has been created (by another process/thread/...) after your test with Exists() but before your call of CreateDirectory(). These are two calls and they are not atomic (together) when querying/modifying the file system.
回答4:
You can also use Path.GetInvalidFileNameChars()
to check whether the directory name supplied is valid for a new directory name:
// Directory.Exists will return false because path is not even valid
var path = "1:1 comparison?";
var firstBad = Path.GetInvalidFileNameChars().Cast<char?>()
.FirstOrDefault(c => path.Contains(c.Value));
if (firstBad != null)
Console.WriteLine("Char '{0}' is invalid for a directory name", firstBad.Value);
回答5:
try this
string path = "this is an invalid path";
if (Path.IsPathRooted(path)
{
Directory.CreateDirectory(path);
}
回答6:
I think the simplest way to test if a path is valid and the file exists without raising an exception in C# is to call the unmanaged function PathFileExists directly in shlwapi.dll.
[DllImport("shlwapi.dll", EntryPoint = "PathFileExistsW", SetLastError = true, CharSet = CharSet.Unicode)]
[return: MarshalAs(UnmanagedType.Bool)]
public static extern bool PathFileExists([MarshalAs(UnmanagedType.LPTStr)]string pszPath);
Note that as David writes in his answer, you might nevertheless get an exception when you try to create the directory.
回答7:
You can use a single if-else statement
if(!Directory.Exists(path))
Directory.CreateDirectory(path)
else
//Show user a custom error message
来源:https://stackoverflow.com/questions/13933607/how-to-check-if-path-is-valid-without-using-try-catch