16進(UNICODE)からSJISへの変換

解決


初心者ひで  2005-04-07 21:01:39  No: 89271

お世話になっております。
Byte型(16進)から最終的にSTRING型にSJIS形式で取得したいのですが、
どのような手順を踏めばいいのでしょうか?
aaa(0)=E5
aaa(1)=65    ⇒SJISの"日"を取得

よろしくお願いします。


ガッ  2005-04-07 21:15:02  No: 89272

vb6だとこんなん…?
dim a(0 to 1) as byte
a(0)=&he5:a(1)=&h65
debug.? bs(a)

function bs(byref b() as byte) as string
bs=b
end function


gtk2k  2005-04-07 22:06:45  No: 89273

Dim Bytes() As Byte
Dim strData As String

'バイト配列にはデータが入っているものとする
strData = StrConv(Bytes, vbFromUnicode)

これでたぶんいけたはず。


初心者ひで  2005-04-07 22:22:04  No: 89274

ガッさん、ご返答ありがとうございます。

えっ。。。これだけの処理で実現できてしまうのですか?
確認してみたら確かに"日"が返ってきていました。

実際の変換はどの処理で行なわれているのでしょうか?
ご教授お願いします。


初心者ひで  2005-04-07 22:39:44  No: 89275

gtk2kさん、ご返答ありがとうございます。
早速テストしてみましたが、"?"が返ってきてしまいます。
strConv(文字列,vbFromUnicode)でSJIS⇔UNICODEの相互変換可能と
ヘルプには書いてあるのですが。
Byte型は扱えないということになるのでしょうか?
それとも他に原因が・・・

Dim a(0 To 1) As Byte
Dim bbb As String

a(0) = &HD8: a(1) = &H4E
bbb = StrConv(a, vbFromUnicode)
MsgBox bbb, vbOKOnly


魔界の仮面弁士  2005-04-07 23:09:33  No: 89276

> 実際の変換はどの処理で行なわれているのでしょうか?

そもそも、VB6の内部文字コードは UTF-16 ですので、
変換は不要ですよ。

  Dim a() As Byte
  ReDim a(3)
  a(0) = &HE5
  a(1) = &H65
  a(2) = &HD8
  a(3) = &H4E

  MsgBox a        'Unicodeバイト配列をそのまま渡す。
  MsgBox CStr(a)  '明示的にString型に変換して渡す。
  MsgBox StrConv(a, 0, 1041)  '第2引数にフラグ無し

逆変換も、
  Dim c() As Byte
  c = "日付"
  Debug.Print Hex(c(0)), Hex(c(1)), Hex(c(2)), Hex(c(3))
とするだけですし。

個別に変換したいなら、
  Debug.Print Hex(Asc("日"))
  Debug.Print Hex(AscW("日"))
とか
  Debug.Print Chr(&H93FA)
  Debug.Print ChrW(&H65E5)
となりますね。

> 早速テストしてみましたが、"?"が返ってきてしまいます。
> bbb = StrConv(a, vbFromUnicode)

この結果にあるbbbは、(日本語環境では)Shift_JIS/Windows31J形式の
文字列になっています。変換自体は正しく行われていますよ。

> MsgBox bbb, vbOKOnly

でも、これは問題です。VB6の文字列は、内部バイナリが UTF-16形式の
データになっているべきですから、Shift_JISのバイナリを持つ文字列を、
MsgBox に表示させると、再度変換が行われ、文字が化けます。

ためしに、以下のコードを実行してみてください。

  Dim a() As Byte, b() As Byte
  a = "日付"
  b = StrConv(a, vbFromUnicode)
  Debug.Print Hex(a(0)), Hex(a(1)), Hex(a(2)), Hex(a(3))
  Debug.Print Hex(b(0)), Hex(b(1)), Hex(b(2)), Hex(b(3))

Unicodeデータの "日付" が、正しく Shift_JIS のバイナリになっているはずです。

> それとも他に原因が・・・

勘違いしないでいただきたいのは、これらの変換は、あくまで、
「VB6の文字列の内部処理形式」の話だという事です。

VB6の標準コントロールやMsgBox関数自体は、ANSIベースのウィンドウです。
つまり、Unicodeには対応していないので、注意してください。

ちょっとややこしいのですが、MsgBox 関数などに渡されたデータは、
VBが表示のたびに、Unicode → Shift_JIS変換を自動で行う仕様です。

ですから、Shift_JISのバイナリを渡すと、Unicode → Shift_JIS変換が
さらに行われてしまい、データが破損するというわけですね。


初心者ひで  2005-04-07 23:52:18  No: 89277

魔界の仮面弁士さん、とても分かりやすい解説ありがとうございます。

内部的にはUTF-16形式でデータを扱っているが、
標準コントロール等ではUTF-16に対応してないからなんですね。
Unicode → Shift_JIS変換を自動で
行なっているというのもポイントですね。

扱いに慣れるまでにはまだまだ頭を悩ませそうですが、
考え方自体はすごくよく分かりました!

本当にありがとうございます!


※返信する前に利用規約をご確認ください。

※Google reCAPTCHA認証からCloudflare Turnstile認証へ変更しました。






  このエントリーをはてなブックマークに追加