JavaでShift_JIS変換時に文字化けする原因と対処法(MS932対応)

この記事は約3分で読めます。

先日、Oracleから取得した文字列を Shift_JIS に変換したところ、外字だけ文字化けしました。 調べてみると、いわゆる「Shift_JIS」運用でも、実際は MS932Windows-31J)前提のケースがあるとわかったので、備忘録として残します。

忙しい人向け

Shift_JIS で変換できない文字を含んでいたのが原因でした。 Java側で文字コード指定を Shift_JIS から MS932 に変更したら解消しました。

問題発生時のファイル構成(例)

sample-project/
└─ src/main/java/com/example/charset/Main.java

発生環境

  • Java: 11
  • DB: Oracle
  • 事象: Oracleから取得した文字列をCSV向けにShift_JIS変換すると、一部文字が ? になる

1. 症状

今回の再現文字列は ㈱あいティーブログ です。 Shift_JIS では変換できず、? に置換されました。

import java.nio.charset.Charset;

public class Main {
    public static void main(String[] args) {
        String sample = "㈱あいティーブログ";

        Charset sjis = Charset.forName("Shift_JIS");
        Charset ms932 = Charset.forName("MS932");

        System.out.println(new String(sample.getBytes(sjis), sjis));
        System.out.println(new String(sample.getBytes(ms932), ms932));
    }
}

実行結果(例)

?あいティーブログ
㈱あいティーブログ

2. 原因

  1. Shift_JISMS932 は同じではなく、文字集合に差がある
  2. Shift_JIS で表現できない文字は、変換時に ? へ置換される
  3. 連携先が「Shift_JIS」と書いていても、実装としては MS932 前提のことがある

3. 対処法

変換時の指定文字コードを MS932 に変更します。

import java.nio.charset.Charset;
import java.nio.file.Files;
import java.nio.file.Path;

String body = "会社名\n㈱あいティーブログ";
Charset charset = Charset.forName("MS932");
Files.writeString(Path.of("output.csv"), body, charset);

必要であれば、CharsetEncoderCodingErrorAction.REPORT を指定し、変換不能文字を例外として検知すると運用しやすくなります。

4. まとめ

Javaで日本語ファイル連携をするときは、「Shift_JIS」という表記だけを鵜呑みにしないのが大事でした。 文字化けが起きたら、まず MS932 指定での再現確認をしてみるのが早いです。

5. 参考

コメント

タイトルとURLをコピーしました