web-dev-qa-db-ja.com

URLを通常のWindowsファイル名に変換Java

これを変換する方法はありますか:

_/C:/Users/David/Dropbox/My%20Programs/Java/Test/bin/myJar.jar
_

これに?:

_C:\Users\David\Dropbox\My Programs\Java\Test\bin\myJar.jar
_

.JARアーカイブのフルパスまたは/ binディレクトリを返す次のコードを使用しています。

_fullPath = new String(MainInterface.class.getProtectionDomain()
            .getCodeSource().getLocation().getPath());
_

問題は、getLocation()URLを返し、通常のWindowsファイル名が必要なことです。 getLocation()の後に次を追加しようとしました:

toString()toExternalForm()は両方とも以下を返します。

_file:/C:/Users/David/Dropbox/My%20Programs/Java/Test/bin/
_

getPath()は以下を返します。

_/C:/Users/David/Dropbox/My%20Programs/Java/Test/bin/
_

スペースに変換する必要がある_%20_に注意してください。

これをすばやく簡単に行う方法はありますか?

52
David

現在の推奨事項(JDK 1.7以降では)は、URL→URI→パスに変換することです。したがって、URLをFileに変換するには、Paths.get(url.toURI()).toFile()と言います。 JDK 1.7をまだ使用できない場合は、new File(URI.getSchemeSpecificPart())をお勧めします。

ファイルの変換→URI:最初に、Javaで取得される可能性のあるURIの例をいくつか示します。

_                          -classpath URLClassLoader File.toURI()                Path.toUri()
C:\Program Files          file:/C:/Program%20Files/ file:/C:/Program%20Files/   file:///C:/Program%20Files/
C:\main.c++               file:/C:/main.c++         file:/C:/main.c++           file:///C:/main.c++
\\VBOXSVR\Downloads       file://VBOXSVR/Downloads/ file:////VBOXSVR/Downloads/ file://VBOXSVR/Downloads/
C:\Résume.txt             file:/C:/R%c3%a9sume.txt  file:/C:/Résume.txt         file:///C:/Résume.txt
\\?\C:\Windows (non-path) file://%3f/C:/Windows/    file:////%3F/C:/Windows/    InvalidPathException
_

これらのURIに関するいくつかの観察:

  • URI仕様は、 RFC 1738:URL 、代替 RFC 2396:URI 、代替 RFC 3986:URI 。 (WHATWGには URI仕様 もありますが、ファイルURIの解釈方法は指定しません。)パス内の予約文字は、パーセント引用符で囲まれ、非ASCII文字です。 URI内のURIは、URI.toASCIIString()を呼び出すときにパーセント引用されます。
  • File.toURI()はPath.toUri()よりも悪いです。これは、File.toURI() が異常な非RFC 1738 URI (file://ではなくfile:/を返すためです) /)および Microsoftの優先形式 に従ってUNCパスのURIをフォーマットしません。ただし、これらのUNC URIはFirefoxでは機能しません(Firefoxではfile://///が必要です)。
  • パスはファイルよりも厳密です。 “ \。\”プレフィックス から無効なパスを作成することはできません。 「これらのプレフィックスはパス自体の一部としては使用されません」が、Win32 APIに渡すことができます。

URI→ファイルの変換:上記の例をファイルに変換してみましょう。

_                            new File(URI)            Paths.get(URI)           new File(URI.getSchemeSpecificPart())
file:///C:/Program%20Files  C:\Program Files         C:\Program Files         C:\Program Files
file:/C:/Program%20Files    C:\Program Files         C:\Program Files         C:\Program Files
file:///C:/main.c++         C:\main.c++              C:\main.c++              C:\main.c++
file://VBOXSVR/Downloads/   IllegalArgumentException \\VBOXSVR\Downloads\     \\VBOXSVR\Downloads
file:////VBOXSVR/Downloads/ \\VBOXSVR\Downloads      \\VBOXSVR\Downloads\     \\VBOXSVR\Downloads
file://///VBOXSVR/Downloads \\VBOXSVR\Downloads      \\VBOXSVR\Downloads\     \\VBOXSVR\Downloads
file://%3f/C:/Windows/      IllegalArgumentException IllegalArgumentException \\?\C:\Windows
file:////%3F/C:/Windows/    \\?\C:\Windows           InvalidPathException     \\?\C:\Windows
_

繰り返しますが、Paths.get(URI)を使用するほうがnew File(URI)よりも優先されます。これは、PathがUNC URIを処理し、\?\プレフィックスを持つ無効なパスを拒否できるためです。ただし、Java 1.7を使用できない場合は、代わりにnew File(URI.getSchemeSpecificPart())と言います。

ところで、donotURLDecoderを使用してファイルURLをデコードします。 「file:/// C:/main.c++」などの「+」を含むファイルの場合、URLDecoderは「C:\ main.c」に変換します! URLDecoderは、URIのクエリ(_param=value&param=value_)内のapplication/x-www-form-urlencoded HTMLフォーム送信の解析のみを目的としており、URIのパスの引用解除は目的外です。

2014-09:サンプルを追加するために編集されました。

72
yonran
String path = "/c:/foo%20bar/baz.jpg";
path = URLDecoder.decode(path, "utf-8");
path = new File(path).getPath();
System.out.println(path); // prints: c:\foo bar\baz.jpg
17
Bozho

前述のとおり、getLocation()はURLを返します。ファイルはURIをパスに簡単に変換できるので、私にとって最も簡単な方法は次のとおりです。

File fullPath = new File(MainInterface.class.getProtectionDomain().
    getCodeSource().getLocation().toURI());

もちろん、文字列が本当に必要な場合は、次のように変更するだけです。

String fullPath = new File(MainInterface.class.getProtectionDomain().
    getCodeSource().getLocation().toURI()).toString();

URLDecoderはまったく必要ありません。

3
Mi-La

こんにちは、未来の人々を混乱させました。ここでは、ファイルパス構成に微妙な違いがあります。 TESSDATA_PREFIXに設定するパスは、C++ tesseractプログラムによって内部的に使用されます。not Javaラッパー。これは、ウィンドウを使用している場合、先頭のスラッシュを置き換え、他のすべてのスラッシュをバックスラッシュに置き換えます。非常にハッキングされた回避策は次のようになります。

URL pathUrl = this.getClass().getResource(TESS_DATA_PATH);
String pathStr = pathUrl.getPath();

// hack to get around windows using \ instead of /
if (SystemUtils.IS_OS_WINDOWS) {
  pathStr = pathStr.substring(1);
  pathStr = pathStr.replaceAll("/", "\\\\");
}
2
xtro

現在の答えは私には怪しいようです。

Java.net.URL.getFile

このようなファイルURLを有効にします

Java.net.URL = file:/C:/some/resource.txt

これに

Java.lang.String = /C:/some/resource.txt

このコンストラクタを使用できます

new File(url.getFile)

windowsパスを提供する

Java.io.File = C:\some\resource.txt
2
Pete Montgomery

次のコードが必要です。

String path = URLDecoder.decode("/C:/Users/David/Dropbox/My%20Programs/Java/Test/bin/", "UTF-8");
System.out.println(new File(path).getPath());
2