掲示板利用宣言

 次のフォームをすべてチェックしてからご利用ください。

 私は

 題名と投稿者名は具体的に書きます。
 課題の丸投げはしません。
 ソースの添付は「HTML変換ツール」で字下げします。
 返信の引用は最小限にします。
 環境(OSとコンパイラ)や症状は具体的に詳しく書きます。
 返信の付いた投稿は削除しません。
 マルチポスト(多重投稿)はしません。

掲示板2

管理者用メニュー    ツリーに戻る    携帯用URL    ホームページ    ログ    タグ一覧

No.26543

SJISからJISへの変換
投稿者---べた(2006/03/31 18:18:17)


メールの件名を日本語表示にしようとして、SJISからJIS
変換にしています。

SJISからJISへの変換のプログラムを作ってみたのですが、
JISに変換してくれません。
どこがいけないのでしょうか
他に、よい方法とかありますか。

環境は、
Solairs8、UNIX-C、gcc
です。


#include <stdio.h>
#include <stdlib.h>

#define iskanji(c) ((c)>=0x81 && (c)<=0x9F || (c)>=0xE0 && (c)<=0xFC)
#define iskanji2(c) ((c)>=0x40 && (c)<=0xFC && (c)!=0x7F)

void tojis(int *ph, int *pl)
{
    if (*ph <= 0x9F) {
        if (*pl < 0x9F) *ph = (*ph << 1) - 0xE1;
        else *ph = (*ph << 1) - 0xE0;
    } else {
        if (*pl < 0x9F) *ph = (*ph << 1) - 0x161;
        else *ph = (*ph << 1) - 0x160;
    }
    if (*pl < 0x7F) *pl -= 0x1F;
    else if (*pl < 0x9F) *pl -= 0x20;
    else *pl -= 0x7E;
}

void sjistojis(const char *sjis, char *jis)
{
    int c, d;

    while (c = *sjis++) {
        if (iskanji(c)) {
            d = *sjis++;
            if (iskanji2(d)) {
                tojis(&c, &d);
                *jis++ = (c | 0x80);
                *jis++ = (d | 0x80);
            } else {
                *jis++ = c;
                if (*sjis != NULL) *jis++ = d;
            }
        } else {
            *jis++ = c;
        }
    }
    *jis = 0;
}

int main()
{
    char sjis[] = {"テスト"};
    char jis[64];

    memset(jis,'\0',sizeof jis);

    sjistojis(sjis,jis);

    printf("SJIS = [%s]\n",sjis);
    printf("JIS  = [%s]\n",jis);
}




この投稿にコメントする

削除パスワード

発言に関する情報 題名 投稿番号 投稿者名 投稿日時
<子記事> Re:SJISからJISへの変換 26545 Hermit 2006/03/31 19:31:34


No.26545

Re:SJISからJISへの変換
投稿者---Hermit(2006/03/31 19:31:34)


変換の仕方までは良く見ていませんが、
JIS 漢字は、漢字in 漢字out コードを
漢字の前後に入れなければいけないんじゃなかったでしょうか。
(それがなんだったか忘れましたが(^^;)

Unix系だったら EUC でないかな??
JIS 漢字コードを +0x80 したら表示します。
漢字in,out コードは必要ありませんし。


この投稿にコメントする

削除パスワード

No.26547

Re:SJISからJISへの変換
投稿者---べた(2006/03/31 21:59:05)


>変換の仕方までは良く見ていませんが、
>JIS 漢字は、漢字in 漢字out コードを
>漢字の前後に入れなければいけないんじゃなかったでしょうか。
>(それがなんだったか忘れましたが(^^;)
>
>Unix系だったら EUC でないかな??
>JIS 漢字コードを +0x80 したら表示します。
>漢字in,out コードは必要ありませんし。

すみません。
書いてあることが理解できないのですが、


プログラムの方は、変換前と変換後の値が
同じなんです。
シフトJISのままなんです。




この投稿にコメントする

削除パスワード

No.26549

Re:SJISからJISへの変換
投稿者---επιστημη(2006/03/31 23:03:51)


>プログラムの方は、変換前と変換後の値が
>同じなんです。
>シフトJISのままなんです。

ならば何がいけないかわかりそうなものだが。




この投稿にコメントする

削除パスワード

No.26548

Re:SJISからJISへの変換
投稿者---べた(2006/03/31 22:26:30)


すみません。
JISにするためには、漢字IN(0x1B + 0x24 + 0x42)、漢字OUT(0x1B + 0x28 + 0x4A)
が必要でした。

つけてみたのですが、うまくいきませんでした。
変換そのものがわるいのでしょうか。



この投稿にコメントする

削除パスワード

No.26550

Re:SJISからJISへの変換
投稿者---si(2006/04/01 00:27:55)


>すみません。
>JISにするためには、漢字IN(0x1B + 0x24 + 0x42)、漢字OUT(0x1B + 0x28 + 0x4A)
>が必要でした。
>
>つけてみたのですが、うまくいきませんでした。
>変換そのものがわるいのでしょうか。
そういう問題ではなくて、
char は singned char なので、int へ拡張されるときには
sign bitが拡張されます。
sjis判断のマクロは、希望通りの動作してますか?  


この投稿にコメントする

削除パスワード

No.26551

Re:SJISからJISへの変換
投稿者---si(2006/04/01 00:29:48)


疑問:コード変換する関数を使わないのはなぜ?
例えば iconv


この投稿にコメントする

削除パスワード

No.26552

Re:SJISからJISへの変換
投稿者---べた(2006/04/01 14:44:36)


>そういう問題ではなくて、
>char は singned char なので、int へ拡張されるときには
>sign bitが拡張されます。
>sjis判断のマクロは、希望通りの動作してますか?  
sjis判断マクロは、動いて動いていませんでした。
elseの処理に流れていました。

ご指摘の通り、「singned char」を考慮したらsjis判断マクロ
が動きました。
また、「|0x80」を演算しているため、EUCに変換されていました。




この投稿にコメントする

削除パスワード

No.26553

Re:SJISからJISへの変換
投稿者---べた(2006/04/01 16:53:51)


一応、動くものができました。
おかしいところはないと思いますが、何か気がついた点とか
こうしたら良いとか、追加したらいいようなことがありますか。

他に、よい方法とかありますか。

#include <stdio.h>
#include <stdlib.h>

#define GET() ((unsigned char)*sjis++)
#define PUT(c) (*jis++ = (c))
#define iskanji(c) ((c)>=0x81 && (c)<=0x9F || (c)>=0xE0 && (c)<=0xFC)
#define iskanji2(c) ((c)>=0x40 && (c)<=0xFC && (c)!=0x7F)

void tojis(int *ph, int *pl)
{
    if (*ph <= 0x9F) {
        if (*pl < 0x9F) *ph = (*ph << 1) - 0xE1;
        else *ph = (*ph << 1) - 0xE0;
    } else {
        if (*pl < 0x9F) *ph = (*ph << 1) - 0x161;
        else *ph = (*ph << 1) - 0x160;
    }
    if (*pl < 0x7F) *pl -= 0x1F;
    else if (*pl < 0x9F) *pl -= 0x20;
    else *pl -= 0x7E;
}

void sjistojis(const char *sjis, char *jis)
{
    int c, d;
    int IO = 0;

    while (c = GET()) {
        if (iskanji(c)) {
            d = GET();
            if (iskanji2(d)) {
                tojis(&c, &d);
                if (IO == 0) PUT(0x1B), PUT(0x24), PUT(0x42), IO = 1;
                PUT(c), PUT(d);
            } else {
                if (IO == 1) PUT(0x1B), PUT(0x28), PUT(0x42), IO = 0;
                PUT(c);
                if (*sjis != NULL) PUT(d);
            }
        } else {
            if (IO == 1) PUT(0x1B), PUT(0x28), PUT(0x42), IO = 0;
            PUT(c);
            if (c == 0) break;
        }
    }
    if (IO == 1) PUT(0x1B), PUT(0x28), PUT(0x42);
    *jis = 0;
}

int main()
{
    char sjis[] = {"テスト"};
    char jis[64];

    memset(jis,'\0',sizeof jis);

    sjistojis(sjis,jis);

    printf("SJIS = [%s]\n",sjis);
    printf("JIS  = [%s]\n",jis);
}




この投稿にコメントする

削除パスワード

No.26556

Re:SJISからJISへの変換
投稿者---かずま(2006/04/02 00:04:49)


> #define iskanji(c) ((c)>=0x81 && (c)<=0x9F || (c)>=0xE0 && (c)<=0xFC)

SJIS の 2バイト文字の 1バイト目は確かにそうですが、
JIS に変換できるのは 0xEF までです。

また、tojis() は次のようにも書けます。

void tojis(int *ph, int *pl)
{
    *ph = ((*ph ^ 0xA0) << 1) - ((*pl < 0x9F) ? 0x21 : 0x20);
    *pl -= (*pl < 0x7F) ? 0x1F : (*pl < 0x9F) ? 0x20 : 0x7E;
}



この投稿にコメントする

削除パスワード

No.26557

Re:SJISからJISへの変換
投稿者---こだま(2006/04/02 10:13:06)


あっているとはおもうのですが、
        } else {
            if (IO == 1) PUT(0x1B), PUT(0x28), PUT(0x42), IO = 0;
            PUT(c);
            if (c == 0) break;
        }


「if (c == 0) break;」
は、必要なのでしょうか。
MULLになった時点でループが終了するで、不要な処理だと
思うのですが、

>> #define iskanji(c) ((c)>=0x81 && (c)<=0x9F || (c)>=0xE0 && (c)<=0xFC)

教えて欲しいのですが、
>SJIS の 2バイト文字の 1バイト目は確かにそうですが、
>JIS に変換できるのは 0xEF までです。
文字コードの変換についてあまり詳しくないのですが、
0xEFを超えた場合どうなるんですか。
どう対処するのいいですか。
どのようなコードになるんですか。
向学のため。






この投稿にコメントする

削除パスワード

No.26558

Re:SJISからJISへの変換
投稿者---επιστημη(2006/04/02 12:04:48)


>>JIS に変換できるのは 0xEF までです。
>文字コードの変換についてあまり詳しくないのですが、
>0xEFを超えた場合どうなるんですか。
>どう対処するのいいですか。

- エラーとして変換をそこまでで止める
- 変換できないからそのままにしておく
- 涼しい顔して変換し、結果は保証しない

などなど、「できないことをやれと言われたとき」の振る舞いはあなたが決めることです。



この投稿にコメントする

削除パスワード

No.26559

Re:SJISからJISへの変換
投稿者---べた(2006/04/03 18:40:33)


かずまさん、επιστημηさん
ありがとうございます。

変換できない場合は、自分で考えないと行けないですね。
それが、仕様ですから。


この投稿にコメントする

削除パスワード

No.26560

Re:SJISからJISへの変換
投稿者---こだま(2006/04/05 00:19:57)


>- エラーとして変換をそこまでで止める
>- 変換できないからそのままにしておく
>- 涼しい顔して変換し、結果は保証しない
>
>などなど、「できないことをやれと言われたとき」の振る舞いはあなたが決めることです。
>
そうですよね。
やる人がどうすか決めることですね。
ただ、皆さんがどう、対処、どう考えてられているのか知りたかっただけでした。



この投稿にコメントする

削除パスワード

No.26561

Re:SJISからJISへの変換
投稿者---επιστημη(2006/04/05 00:45:21)


>ただ、皆さんがどう、対処、どう考えてられているのか知りたかっただけでした。

僕なら「最も楽な実装」となるよう、仕様を決めます。



この投稿にコメントする

削除パスワード

管理者用メニュー    ツリーに戻る    携帯用URL    ホームページ    ログ    タグ一覧