如何建立相对于特定文件夹的绝对路径?

asm*_*smo 25 .net c# path

例如,我该怎么做呢

"C:\RootFolder\SubFolder\MoreSubFolder\LastFolder\SomeFile.txt"
Run Code Online (Sandbox Code Playgroud)

相对于此文件夹

"C:\RootFolder\SubFolder\"
Run Code Online (Sandbox Code Playgroud)

如果预期的结果是

"MoreSubFolder\LastFolder\SomeFile.txt"
Run Code Online (Sandbox Code Playgroud)

ord*_*dag 39

是的,你可以这样做,很容易,把你的路径想象成URI:

Uri fullPath = new Uri(@"C:\RootFolder\SubFolder\MoreSubFolder\LastFolder\SomeFile.txt", UriKind.Absolute);
Uri relRoot = new Uri(@"C:\RootFolder\SubFolder\", UriKind.Absolute);

string relPath = relRoot.MakeRelativeUri(fullPath).ToString();
// relPath == @"MoreSubFolder\LastFolder\SomeFile.txt"
Run Code Online (Sandbox Code Playgroud)

  • `relPath = Uri.UnescapeDataString(relPath)`来修复空格. (5认同)
  • 如果根路径不以“\”结尾,则根路径的最后一部分不会从完整路径中删除! (3认同)
  • 虽然这是一个可以工作的 hack,但它并不是原始帖子的解决方案。 (2认同)

das*_*ght 15

在你的例子中,它很简单absPath.Substring(relativeTo.Length).

更详细的例子需要从relativeTo以下几个级别返回:

"C:\RootFolder\SubFolder\MoreSubFolder\LastFolder\SomeFile.txt"
"C:\RootFolder\SubFolder\Sibling\Child\"
Run Code Online (Sandbox Code Playgroud)

制作相对路径的算法如下所示:

  • 删除最长的公共前缀(在这种情况下,它是"C:\RootFolder\SubFolder\")
  • 计数的文件夹的数量relativeTo(在这种情况下,为2: "Sibling\Child\")
  • 插入..\每个剩余的文件夹
  • 在删除后缀后与绝对路径的其余部分连接

最终结果如下:

"..\..\MoreSubFolder\LastFolder\SomeFile.txt"
Run Code Online (Sandbox Code Playgroud)


Chr*_*ler 5

对于现代实现,请使用System.IO.Path.GetRelativePath

Path.GetRelativePath(String, String) 方法
返回从一个路径到另一路径的相对路径。

public static string GetRelativePath (string relativeTo, string path);
Run Code Online (Sandbox Code Playgroud)

在.Net Core 2.0(2017年8月)和.Net Standard 2.1(2018年5月)中引入,其实现与@TarmoPikaro发布的答案非常相似

该方法的用法:

string itemPath = @"C:\RootFolder\SubFolder\MoreSubFolder\LastFolder\SomeFile.txt";
string baseDirectory = @"C:\RootFolder\SubFolder\";

string result = System.IO.Path.GetRelativePath(baseDirectory, itemPath);
Console.WriteLine(result);
Run Code Online (Sandbox Code Playgroud)

结果是:

MoreSubFolder\LastFolder\SomeFile.txt
Run Code Online (Sandbox Code Playgroud)

@TarmoPikaro 的答案一样,此实现利用System.IO.Path.GetFullPath来解析比较之前通过的潜在相对路径。

其背后的目的是解析通过附加基本路径相对路径而构造的路径,我们经常在调用之前在代码中执行此操作GetRelativePath()。它应该解决以下问题:

"c:\test\..\test2" => "c:\test2"
Run Code Online (Sandbox Code Playgroud)

这是预期的,但如果输入路径是完全相对的,路径将解析为当前工作文件夹,在我的测试应用程序中,如下所示:

".\test2" => "D:\Source\Repos\MakeRoot\bin\Debug\net6.0\test2"
Run Code Online (Sandbox Code Playgroud)

在大多数情况下,这会导致意想不到的结果MakeRelative。因此,实际上期望您使用串联或您自己的调用来解析输入参数GetFullPath