1

Java 文字を JIS X 0208 "x-JIS0208" エンコーディング (または、Shift-JIS ではなく EUC-JP などの互換性のあるエンコーディング) に変換しようとしていますが、統合 (マージ) コードポイントを正しく処理したいと考えています。

たとえば、この JISX0208 チャートでは、25 行 66 列に「高」が割り当てられており、類似文字の「髙」は、割り当てられていないコードポイントに分類されますが、前者とマージされます。ウィキペディアから引用します。「フォーム [ ] (高) と、はしごのような構造を持つあまり一般的でないフォーム (髙) の両方が、同じコード ポイントに組み込まれています」。

以下のコードでこれを試してみましたが、どのエンコーディングを試しても、常に例外または割り当てられていない文字プレースホルダー?(ASCII または全角) が発生します。

おそらく異なるエンドディングまたはまったく異なる変換方法があるので、これらの文字は両方とも同じコードポイントを返しますか? または、そのような文字を検索して変換する前にマージできる API はありますか?

static Charset      charset1    = Charset.forName("x-JIS0208");
static Charset      charset2    = Charset.forName("EUC-JP");
static Charset[]    charsets    = {charset1, charset2};

static CharBuffer   in          = CharBuffer.allocate(1);

public static void main(String[] args) throws Exception
{
    CharsetEncoder[] encoders = new CharsetEncoder[charsets.length];
    for (int i = 0; i < charsets.length; i++)
        encoders[i] = charsets[i].newEncoder();

    char[] testChars = {' ', 'A', '?', '亜', '唖', '蔭', '高', '髙'};

    for (char ch : testChars)
    {
        System.out.print("'" + ch + "'\t(" + Integer.toHexString(ch) + ")\t=");

        for (int i = 0; i < charsets.length; i++)
        {
            System.out.print("\t" + interpret(encode1(encoders[i], ch)));
            System.out.print("\t" + interpret(encode2(charsets[i], ch)));
        }
        System.out.println();
    }
}

private static String interpret(int i)
{
    if (i == -1)
        return "excepti";
    if (i < 0x80)
        return "'" + (char)i + "'";
    return Integer.toHexString(i);
}

private static int encode1(CharsetEncoder encoder, char ch)
{
    in.rewind();
    in.put(ch);
    in.rewind();

    try
    {
        ByteBuffer out = encoder.encode(in);

        if (out.limit() == 1)
            return out.get(0) & 0xFF;
        return out.get(1) & 0xFF | (out.get(0) & 0xFF) << 8;
    }
    catch (CharacterCodingException e)
    {
        return -1;
    }
}

private static int encode2(Charset charset, char ch)
{
    in.rewind();
    in.put(ch);
    in.rewind();

    ByteBuffer out = charset.encode(in);

    if (out.limit() == 1)
        return out.get(0) & 0xFF;
    return out.get(1) & 0xFF | (out.get(0) & 0xFF) << 8;
}

出力:

' ' (3000)  =   2121    2121    a1a1    a1a1
'A' (ff21)  =   2341    2341    a3c1    a3c1
'?' (ff1f)  =   2129    2129    a1a9    a1a9
'亜' (4e9c)  =   3021    3021    b0a1    b0a1
'唖' (5516)  =   3022    3022    b0a2    b0a2
'蔭' (852d)  =   307e    307e    b0fe    b0fe
'高' (9ad8)  =   3962    3962    b9e2    b9e2
'髙' (9ad9)  =   excepti 2129    excepti '?'

注:文字列やストリームではなく、単一の文字を変換することにのみ関心があるため、実際には、変換ごとに ByteBuffer を割り当てない別の方法(存在する場合)を好みます。

4

2 に答える 2

0

仕様「ARIB STD-B24」(JPのISDB-Tワンセグ用)で、この文字はDRCS-1からDRCS-15までのDRCSパターンデータでコーディングされており、各セットは94文字で構成されていることしか知りませんでした。

于 2013-07-01T06:59:49.150 に答える