文字列からブール配列変換の謎!


こんにちは、ドルフィンシステムの笹生です。
本年もよろしくお願いします。

さて私担当の今年1本目のメールニュースは、「文字列からブール配列変換の謎!」と題してお送りします。

我々の仕事はソフトウェア無線機を使った試作が多くを占めます。
当然、外部からデータを流して通信させたいということも普通にあるわけです。
その中でも UDP 経由で外部から受信したパケットを無線機で送信し、無線機で受信したものを UDP で外部に送信するというような構成はよく使われます。
今回はその UDPデータである文字列から無線ペイロードにするためのブール配列への変換について魔訶不思議な現象が起きましたのでご紹介したいと思います。

UDP 文字列からビット列であるブール配列への変換、のはずだが。。。


LabVIEWでは UDP の送受信データは文字列を使用します。
その受信した UDP 文字列を無線区間のペイロードに乗せたいのでビット列に変換したい場合があります。
通常、LabVIEW (FPGA でも) でビット列を扱う場合はブール配列を用いることが多いので、UDP の文字列からブール配列に変換することが必要です。

LabVIEW では「型変換」という関数で型を変更でき、非常に簡単にできそうだったので使用してみます。
こんな VIを用意しました。

こちらからダウンロードできます。(LabVIEW 2016以降で開きます)

流れの説明です。
送信模擬の部分で、文字列からブール配列に「型変換」関数でブール配列に変換し、受信模擬部分では変換されたブール配列を「型変換」関数で文字列に戻します。

例えばこの例のように文字列に "dolphin" 7文字の文字列を指定してみます。
通常この文字列は1文字1Byte 相当なので、ビット列のブール配列としては 7*8=56bit になると期待されます。ブール配列の要素数サイズも表示できるようにしてあります。
しかし実行してみると、、、

7bit?

たしかにブール配列は 7bit 分しかありません。しかも全部 TRUE=1

ですが、そのブール配列を文字列に戻すとちゃんと"dolphin" という文字列に戻ります。
1文字が1bit に圧縮されたのでしょうか???
もしかしてLabIVEW は量子ビットの扱いを先取りして実装しているのでしょうか???

冗談はともかく、正しくブール配列に変換できないのであれば、本来元の文字列に戻るはずはありません。

文字列を "dol" にすると3bit になります。ですので文字数と要素数サイズは一致しているようです。
元に戻るのですから、どこかに情報が残っているのかもしれません。でも多分最初からこのブール配列の値を変換しても絶対に "dolphin" にはならないわけですよね。7bit なら 1文字にも満たない。
でも7文字7bit に変換できるなら、このビット列を無線で送信できれば 1/8 のサイズに圧縮できてすごいことになりそうですが。。。
実際にはできませんでした。当たり前ですが。
ということでこれは型変換の仕様なのかバグなのか不明ですが、このやり方はダメです。これでできたら簡単でいいのですけど。。。

正しく変換するには・・・


ではどう変換するのが正解でしょうか。以下正解です。

こちらからダウンロードできます。

こちらが今のところ正しいやり方になりそうです。(もっとシンプルな方法があれば是非教えてください)
送信側、文字列からブール配列にするには、まず「文字列をバイト配列に変換」関数でバイト配列にし、それを For ループで 1つづつ、数値を「ブール配列に変換」でブール配列に変換します。そして For の出口でそれらを1次元配列として連結します。

一方受信側のほうでは、ブール配列を 8bit 毎の 2次元配列にして、For ループで 8bit 毎に「ブール配列を数値に変換」して「U8」にキャストします。For の出口でバイト配列にし、「バイト配列を文字列に変換」関数で文字列に戻します。

ここで使用している「文字列をバイト配列に変換」関数や「バイト配列を文字列に変換」関数では「型変換」関数をし

いずれにしても一旦バイト配列のような数値配列にしてから変換することが基本のようです。

まとめ

UDP経由での送受信の際、ペイロードとしてビット列であるブール配列への変換についての方法について解説してみました。
一番簡単にできそうだった「型変換」関数を使っての変換がうまくいかなかった(のに逆変換がうまくいく)のですが、バイト配列に一度変換すればうまくいくことがわかりました。

0 件のコメント :

コメントを投稿