How to use Path.Combine with more than two arguments?

I am surprised that there is no overload that can take a string array. Anyway, the best way to avoid making calls on Path.Combine?

pathValue = Path.Combine(path1, Path.Combine(path2, Path.Combine(path3, path4))) 

This seems inefficient, as it results in 4 new lines to get 1.

+20
string io path concatenation
Apr 17 '09 at 14:23
source share
3 answers

The effective side of things is not the IMO problem - it is the usability side. Personally, I think there should be an overload:

 Combine(string first, string second, string third, params string[] others) 

You should have at least three so that it does not collide with the existing two-parameter version if you just write Path.Combine("foo", "bar") , but this will certainly help make the code more understandable. Why not open a feature request on Connect ?

Of course, you can implement this yourself (and in another class, the number of parameters does not matter much):

 public static string CombinePaths(string first, params string[] others) { // Put error checking in here :) string path = first; foreach (string section in others) { path = Path.Combine(path, section); } return path; } 
+20
Apr 17 '09 at 14:33
source share

If you already have an array or IEnumerable, you can do it on one line ...

 // I'm assuming that you've got an array or IEnumerable<T> from somewhere var paths = new string[] { path1, path2, path3, path4, path5, path6 }; string result = paths.Aggregate(Path.Combine); 

If not, what about writing your own extension method for the string ...

 public static class PathExtension { public static string CombinePathWith(this string path1, string path2) { return Path.Combine(path1, path2); } } 

... which allows you to link them like this:

 string result = path1.CombinePathWith(path2) .CombinePathWith(path3) .CombinePathWith(path4) .CombinePathWith(path5) .CombinePathWith(path6); 
+25
Apr 17 '09 at 14:51
source share

It is very simple to implement it yourself:

 public string Combine(params string[] paths) { char[] pathSeparators = new char[] { Path.AltDirectorySeparatorChar, Path.DirectorySeparatorChar, Path.VolumeSeparatorChar }; if(paths == null) throw new ArgumentNullException("paths"); if(paths.Length == 1) return paths[0]; StringBuilder pathBuilder = new StringBuilder(); foreach(string path in paths) { if(Path.IsPathRooted(path)) pathBuilder = new StringBuilder(path); else { char last = pathBuilder.Length > 0 ? pathBuilder[pathBuilder.Length - 1] : path[path.Length - 1]; if(Array.IndexOf(pathSeparators, last) == -1) pathBuilder.Append(Path.DirectorySeparatorChar); pathBuilder.Append(path); } // else } // foreach return pathBuilder.ToString(); } [Test()] public void CombinePaths() { string result = Combine(@"C:\Program Files\", @"Microsoft.NET", @"ADOMD.NET\", "90", "msadomdx.dll"); Assert.AreEqual(@"C:\Program Files\Microsoft.NET\ADOMD.NET\90\msadomdx.dll", result); } 
+1
Apr 17 '09 at 14:40
source share



All Articles