2012年5月7日月曜日

エンコーディング - encoding(国際化/日本語化)

[S146-Q01]



String文字列をShift-JISや日本語EUCに変換したいのですが?


[S146-A01]
String#getBytes(String enc)を使用しましょう。
encに目的のエンコードを示す文字列を指定すると、指定したエンコードで変
換されたbyte配列が取得できます。

(例) Shift-JISのbyte配列を取得する。
String string = "テスト";
byte[] sjisBytes = string.getBytes("SJIS");

参考記事 [JavaHouse-Brewers:9873]



[S146-Q02]



Shift-JISや日本語EUCの文字列からStringを作るには?


[S146-A02]
new String(byte[] b, String enc)を使用しましょう。
Stringのコンストラクタで、bに文字列が格納されたバイト配列を、encにその
バイト配列の文字エンコーディングを指定すると、Stringオブジェクトが作ら
れます。

(例) Shift-JISのbyte配列からStringオブジェクトを生成する。
byte[] sjisBytes; // Shift-JISのbyte配列
String string = new String(sjisBytes, "SJIS");

参考記事 [JavaHouse-Brewers:9968]



[S146-Q03]



文字列を扱う要素が byte[], char[], String, StringBuffer などいろいろあ
るようですが、どう使い分けたら?


[S146-A03]
基本的に、次のように考えるとよいでしょう。
・byte[]…Unicode以外のエンコードの文字を1バイトづつ格納する配列。
・char[]…Unicode文字を1文字づつ格納する配列。
・String…Unicode文字列のRead Only表現
・StringBuffer…Unicode文字列操作のためのオブジェクト。

各要素間の変換で良く使われるものを挙げておきます。
・byte[]に文字コードを格納して、エンコーディング変換しながらStringに変

・Stringをエンコーディング変換してbyte[]に格納
・char[]にUnicode文字を格納してからStringに変換
・StringをStringBufferに変換し、StringBufferで文字列の結合、挿入などの
文字列操作を行ってからStringに変換

参考記事 [JavaHouse-Brewers:13287]



[S146-Q04]



デフォルトのエンコーディングを変えようとして、java -Dfile.encoding...
とオプションを変えてもうまく動きません。なぜ?


[S146-A04]
JDK1.2以降は、実行時にデフォルトのエンコーディングを変更する方法がない
ようです。
file.encoding プロパティを指定して java を起動しても無視されます。
現在、改善要求が
http://developer.java.sun.com/developer/bugParade/bugs/4175635.html
に登録されていますが、直されていません。

参考記事 [JavaHouse-Brewers:21272],[JavaHouse-Brewers:16640],[JavaHouse-Brewers:9141]



[S146-Q05]



Javaで指定できるエンコーディング名にはどのようなものが?


[S146-A05]
Sunが公開しているエンコーディング名一覧は、以下のURLで入手可能です。

JDK 1.1
http://www.javasoft.com/products/jdk/1.1/docs/guide/intl/encoding.doc.html

JDK 1.2
http://www.javasoft.com/products/jdk/1.2/docs/guide/internat/encoding.doc.html

JDK 1.3
http://java.sun.com/j2se/1.3/docs/guide/intl/encoding.doc.html

指定可能なエンコーディング(より正確には、Unicodeと他のエンコーディング
とのコンバータ)の名前は、上記のURLで示されているものの他に、IANAで管理
されていたcharset名などもエイリアス(別名)として実現されています。

Sunが公開している上記のURLでは、エイリアスについて言及されていません。
エイリアスを含めた指定可能エンコーディング名一覧、関連情報については、
風間一洋氏が独自に解析し、以下のURLで公開しています.
http://www.ingrid.org/java/i18n/encoding/

なお、コンバータ名は大文字・小文字を区別しますが、エイリアス名はそれら
の区別をしないことに注意が必要です。



[S146-Q06]



Javaにおける文字コードの話で、時々「MS932」「CP932」「CP930」「CP939」
という言葉が出てきますが?


[S146-A06]
IBMやMicrosoftが定義したコードページ(文字集合の各要素に符号位置を割り
当てたもの)を識別する記号です。Javaでは、エンコーディング名として定義
されており、これらを用いて各コードページとUNICODEとの相互変換が可能で
す。

コンバータ名の中で、"MS"という接頭辞がついているものは、Microsoftの独
自仕様を示します。MicrosoftとIBMのコードページには、同じ番号でも相違点
があることがあり、その場合には、IBMはCP、MicrosoftはMSという接頭辞を番
号の前に付けて、コンバータを区別しているようです。



[S146-Q07]



Shift-JISや日本語EUCやJISの日本語コードを自動認識して読み込みたいのですが?


[S146-A07]
"JISAutoDetect"をエンコード指定することにより、ある程度の識別が可能です。
ただし、Shift-JISで書かれた'−'や'〜'などの文字を読み込む場合、
JDK1.1.8, JDK1.2以降のWindows環境とそれ以外のプラットフォームでは、
UNICODEへの変換方法に違いがあるので注意が必要です。

参考記事 [JavaHouse-Brewers:9995]



[S146-Q08]



デフォルトのエンコーディングがJISAutoDetectだと便利だと思うのですが、
そうなっていないのは何故?


[S146-A08]
JISAutoDetect は読み込み専用のエンコーディング名です。出力時に指定する
ことは許されていません。

JISAutoDetect は、JIS, Shift-JIS, 日本語EUCのいずれかのエンコーディン
グを自動識別して読み込み、Unicodeに変換します。出力時のエンコーディン
グを「自動識別」するという概念はないため、OutputStreamWriter などで
JISAutoDetect を指定すると UnsupportedEncodingException 例外が発生しま
す。

また、現在のJDKの実装では、デフォルトエンコーディング指定は入力と出力
とで同じものしか指定できないため、上記の理由により、JISAutoDetect はデ
フォルトエンコーディングに指定されていません。

参考記事 [JavaHouse-Brewers:12964],[JavaHouse-Brewers:13745]



[S146-Q09]



'−'や'〜'が文字化けします。他の文字は文字化けしていないのになぜ?


[S146-A09]
WindowsとUNIXなど、異なるプラットフォーム間でコンパイルや実行を行って
いませんか?
・日本語文字列を含むソースをコンパイルして、UNIXで実行(もしくは逆)
・WindowsとUNIX間での日本語文字列の受け渡し
上記のような振舞いによっては'−'や'〜'を始めとする一部の文字が正しく表
示されない現象が確認されています。

理由は、Windows環境のデフォルトコンバータである"MS932"(JDK1.1.8, 1.2以
降)と、その他の"JIS", "SJIS", "EUCJIS"とでは、同じ文字が異なるUNICODE
文字へマッピングされてしまうからです。

(例) '〜' をUNICODEへマッピングする場合
"JIS", "SJIS", "EUCJIS" を使用 → U+301C (WAVE DASH)
"MS932" を使用 → U+FF5E (FULLWIDTH TILDE)

このような文字を、一方のプラットフォームから他方へ受け渡して処理しよう
しても正しく処理されない可能性があります。
同様の理由で、MacOSと他のプラットフォームとでは、'…'の文字が影響を受
けます。

この問題はJDKのバージョン(JDK1.1.8, 1.2以降とそれ以外)によって挙動が
異なるため、注意が必要です。

この問題を根本的に解決する方法は今のところなく、正しい処理が行われるよ
うに、適時文字コード変換を行うしかありません。

この問題の対処法や詳しい情報は、風間一洋氏がJavaHouseメーリングリスト
上で公開した、文字コード変換フィルタ
http://java-house.etl.go.jp/ml/archive/j-h-b/014452.html
や、同氏のWebサイトにある「日本語のUnicodeベンダ依存文字表」
http://www.ingrid.org/java/i18n/unicode.html
を参考にしてください。

参考記事 [JavaHouse-Brewers:25058]



[S146-Q10]



JISAutoDetectで入力した元の漢字コードが何か知りたいのですが?


[S146-A10]
直接問題を解決できるAPIは用意されていませんが、Shift-JIS、JIS、日本語
EUC を指定して得られる3種類の String を、自動判別で得た String と比較
するという方法を使えば識別は可能です。

参考記事 [JavaHouse-Brewers:28949],[JavaHouse-Brewer:27372]



[S146-Q11]



MicrosoftのJavaで、エンコーディング名に"EUCJIS" を指定しても
UnsupportedEncodingException 例外が発生します。どうすれば?


[S146-A11]
MicrosoftのVMは、標準ではEUCをサポートしていません。追加パッケージのみ
の提供となっています。
http://www.microsoft.com/java/resource/misc.htm
"Additional I/O libraries" のリンクからたどれる ftp サイトから
sunio114.zip をダウンロードし、クラスパスに追加してください。
上記 ftp サイトで見つからない場合は以下の URL からダウンロードしてください。
ftp://ftp.sunet.se/pub3/vendor/microsoft/developr/MSDN/UnSup-ed/

0 件のコメント:

コメントを投稿