- PR -

構造体のメンバの型に参照型が含まれる場合、byte配列に変換できるの?

1
投稿者投稿内容
未記入
常連さん
会議室デビュー日: 2007/05/01
投稿数: 35
投稿日時: 2007-05-15 20:21
お世話になっております。

構造体をbyte[]にコピーするスレッドが以前たっていましたが、
それについて追加で質問させていただきます。
以前のスレッドのURLは↓
http://www.atmarkit.co.jp/bbs/phpBB/viewtopic.php?topic=6961&forum=7

構造体のメンバにstringやbyte[](参照型)が存在する場合、
CopyMemoryで構造体をbyte[]に変換することは可能なのでしょうか?

現在、単純なソケット通信プログラムを作成しており、
ざっくりと以下のような状態です。

  '送信する構造体
Public Structure sendStructure
Public first As Integer
Public second As Integer
Public third As Integer
Public moji As String
End Structure

Dim data_byte(Len(data_structure) - 1) As Byte
  Dim data_structure As sendStructure

  '送信するバイト配列の先頭アドレスを取得
Dim gch1 As GCHandle
gch1 = GCHandle.Alloc(data_byte, GCHandleType.Pinned)
Dim pointer1 As Integer = gch1.AddrOfPinnedObject()

  '送信したい構造体の先頭アドレスを取得
Dim gch2 As GCHandle
gch2 = GCHandle.Alloc(data_structure, GCHandleType.Pinned)'★★★エラー発生
Dim pointer2 As Integer = gch2.AddrOfPinnedObject()

  Dim client As New TcpClient(host, port)
  
  Dim stream As NetworkStream = client.GetStream()
Dim binaryWriter As BinaryWriter = New BinaryWriter(stream)

'構造体のデータをバイト配列にコピー
CopyMemory(pointer1, pointer2, Len(data_structure))

  binaryWriter.Write(data_byte)

という感じです。

エラー内容は、
「オブジェクトに、プリミティブでないか、または blittable でないデータが含まれています。」です。

構造体のメンバが全てプリミティブ型であれば、Alloc関数でエラーも発生せず、
ソケット通信は可能です。

どなたか解決策を教えていただけないでしょうか?

Hongliang
ぬし
会議室デビュー日: 2004/12/25
投稿数: 576
投稿日時: 2007-05-15 21:14
その文字列/配列が固定長なら、バイト配列との C 言語的な変換は可能です。
詳しくは MSDN で「相互運用マーシャリング」のトピックをご覧ください。
サンプルも豊富です。

固定長ではない文字列/配列の場合、C 言語的に考えても、メンバにあるのはポインタだけで、実体はどこか別の場所ですよね?
その辺はどうするんですか?

ちなみに、通信形式を自分で決められる上に自分も相手も .NET なら、BinaryFormatter とかでやるのが手っ取り早いです。

[ メッセージ編集済み 編集者: Hongliang 編集日時 2007-05-15 21:14 ]
未記入
常連さん
会議室デビュー日: 2007/05/01
投稿数: 35
投稿日時: 2007-05-19 19:33
相互運用マーシャリングのトピックを読みました。
ん〜理解できません。。。

結局、構造体をあきらめ、クラスを定義し、そのメンバ要素をbyte配列に変換する
関数を作成することで解決できました。

ありがとうございました。


1

スキルアップ/キャリアアップ(JOB@IT)