我在java.io包中有一种方法可以将包含“../”的相对路径转换为绝对路径吗?
我的目标是删除路径的“../”部分,因为
java.awt.Desktop.getDesktop().open()
在Windows
下的文件路径中似乎不支持../答案 0 :(得分:1)
---当评论说明../仍然在路径---
时编辑import java.io.File;
public class Test {
public static void main(String[] args) throws Exception {
File file = new File("../../home");
System.out.println(file.getCanonicalPath());
System.out.println(file.getAbsolutePath());
}
}
将与输出
一起运行/home/ebuck/home
/home/ebuck/workspace/State/../../home
基于我当前的工作目录/home/ebuck/workspace/State
请注意,您要求提供完整的实际文件路径,从技术上讲,绝对路径是完整的实际文件路径,它不是最短的完整实际文件路径。因此,如果你想快速而又脏,那么可以将“../../home”添加到当前工作目录并获得完整,完整的文件路径(尽管是包含不必要信息的罗嗦文件路径)。 / p>
如果您希望最短完整,完整的文件路径,那就是getCanonicalPath()
的用途。它引发了一个例外;因为,在根目录中,一些小丑可能会要求“../../home”。
---原帖如下,编辑---
new File("../../dir/file.ext").getCanonoicalPath();
这样做会折叠(跟随)相对路径链接(.
和..
)。
new File("../../dir/file.ext").getAbsolutePath();
不会折叠(跟随)相对路径链接。
答案 1 :(得分:0)
String path = new File("../../dir/file.ext").getCanonicalPath();
答案 2 :(得分:0)
File f = new File("..");
String path = f.getAbsolutePath();
答案 3 :(得分:0)
有时可能不需要File.getCanonicalPath(),因为它可能会解决诸如符号链接之类的问题,因此如果要维护File.getAbsolutePath()提供的“逻辑”路径,则不能使用getCanonicalPath()。此外,IIRC,gCP()可以抛出异常而gAP()没有,并且gAP()可以引用不存在的路径。
很久以前我遇到过'..'问题。这是我写的一个实用方法,用于删除路径中的'..':
/**
* Retrieve "clean" absolute path of a file.
* <p>This method retrieves the absolute pathname of file,
* with relative components (e.g. <tt>..</tt>) removed.
* Java's <tt>File.getAbsolutePath()</tt> does not remove
* relative components. For example, if given the pathname:
* </p>
* <pre>
* dir/subdir/subsubdir/../../file.txt
* </pre>
* <p>{@link File#getAbsolutePath()} will return something like:
* </p>
* <pre>
* /home/whomever/dir/subdir/subsubdir/../../file.txt
* </pre>
* <p>This method will return:
* </p>
* <pre>
* /home/whomever/dir/file.txt
* </pre>
*
* @param f File to get clean absolute path of.
* @return Clean absolute pathname of <i>f</i>.
*/
public static String cleanAbsolutePath(
File f
) {
String abs = f.getAbsolutePath();
if (!relDirPattern.matcher(abs).find()) {
// Nothing to do, so just return what Java provided
return abs;
}
String[] parts = abs.split(fileSepRex);
ArrayList<String> newPath = new ArrayList<String>(parts.length);
int capacity = 0;
for (String p : parts) {
if (p.equals(".")) continue;
if (p.equals("..")) {
if (newPath.size() == 0) continue;
String removed = newPath.remove(newPath.size() -1);
capacity -= removed.length();
continue;
}
newPath.add(p);
capacity += p.length();
}
int size = newPath.size();
if (size == 0) {
return File.separator;
}
StringBuilder result = new StringBuilder(capacity);
int i = 0;
for (String p : newPath) {
++i;
result.append(p);
if (i < size) {
result.append(File.separatorChar);
}
}
return result.toString();
}
/** Regex string representing file name separator. */
private static String fileSepRex = "\\"+File.separator;
/** Pattern for checking if pathname has relative components. */
private static Pattern relDirPattern = Pattern.compile(
"(?:\\A|" + fileSepRex + ")\\.{1,2}(?:" + fileSepRex + "|\\z)");