タイトル : Re^4: 入れ子の構造体へのバイト配列のセットについて 投稿日 : 2012/11/18(Sun) 11:50 投稿者 : 九州男児
> > Public Shared KYOBI1 As Byte() = New Byte(27) {} > > Public Shared KTutatuNo() As Byte = New Byte(1) {} > > 「Dim var() As Type」か > 「Dim var As Type()」かを統一しましょう。 > どちらも同じ意味とはいえ、混在しているのは見苦しいので。 > > なお、VBでは前者の書き方が標準的です。 > > > > > Newでサイズを指定した場合、「Shared」をつけないとエラーになったのですが。 > この場面で、Shared を使うべきではありません。たとえば、 > Dim a As pcKIROKU, b As pcKIROKU > a.KYOBI1(0) = 10 > b.KYOBI1(0) = 20 > a.KZokusei = 100 > b.KZokusei = 200 > のような使い方をしたいなら、Shared は使えないことになります。 > > Shared にすると、構造体変数ではなく構造体そのもので値が管理されるため、 > 上記 a と b とで、異なる値を保持することができなくなるためです。 > > Dim mcKIROKU(15) As pcKIROKU のように、配列で管理した場合も同様です。 > KZokusei が Shared の場合、mcKIROKU(0).KZokusei や mcKIROKU(1).KZokusei は、 > 結局は「pcKIROKU.KZokusei」の意味になってしまいます。 > > > 初期サイズを設定したいなら、 > (案1) 構造体の代わりにクラスで代用する。 > (案2) 引数付コンストラクタを用意し、そこで配列サイズを初期化する。 > (案3) 現在未使用の Initialize メソッドを利用して、そこで配列サイズを初期化する。 > (案4) VB の代わりに unsafe C# を採用し、fixed (固定サイズの配列)を指定する。 > などの手法で代用してみてください。 > > > 案1 > Public Class pcKIROKU2 > Public KYOBI1(27) As Byte > Public KZokusei As Byte > Public IkisakiCd As Byte > Public KTutatuNo(1) As Byte > Public KTatuHkb(2) As Byte > Public KSekobi(2) As Byte > Public KSigyoKumi(10) As Byte > Public KSigyoNo(1) As Byte > Public KKushoCd As Byte > End Class > > この方法の場合、使う前に New する必要が生じます。 > たとえば > Dim a As New pcKIROKU() > Dim b() As pcKIROKU = { New pcKIROKU(), New pcKIROKU()} > など。 > > New しなかった場合は、クラス変数が Nothing となるため、 > そのまま使うと NullReferenceException の原因となります。 > > > > 案2 > Public Structure pcKIROKU > Public KYOBI1() As Byte > Public KZokusei As Byte > Public IkisakiCd As Byte > Public KTutatuNo() As Byte > Public KTatuHkb() As Byte > Public KSekobi() As Byte > Public KSigyoKumi() As Byte > Public KSigyoNo() As Byte > Public KKushoCd As Byte > > Public Sub New(dummy As Integer) > ReDim KYOBI1(27), KTutatuNo(1) > ReDim KTatuHkb(2), KSekobi(2) > ReDim KSigyoKumi(10), KSigyoNo(1) > End Sub > End Structure > > この方法の場合、使う前に New する必要が生じます。 > たとえば > Dim a As New pcKIROKU(0) > Dim b() As pcKIROKU = { New pcKIROKU(1), New pcKIROKU(2)} > など。 > > New しなかった場合は、構造体変数が初期値のままとなるため > 各フィールドの配列もまた、初期化されていない状態となります。 > > > > 案3 > Public Structure pcKIROKU > Public KYOBI1() As Byte > Public KZokusei As Byte > Public IkisakiCd As Byte > Public KTutatuNo() As Byte > Public KTatuHkb() As Byte > Public KSekobi() As Byte > Public KSigyoKumi() As Byte > Public KSigyoNo() As Byte > Public KKushoCd As Byte > > Public Sub Initialize() > ReDim KYOBI1(27), KTutatuNo(1) > ReDim KTatuHkb(2), KSekobi(2) > ReDim KSigyoKumi(10), KSigyoNo(1) > End Sub > End Structure > > この方法の場合、使う前に Initialize メソッドを呼ぶ必要が生じます。 > たとえば > Dim a As pcKIROKU > Dim b(1) As pcKIROKU > a.Initilaize() > b(0).Initilaize() > b(1).Initilaize() > など。 > > Initialize を呼ばなかった場合は、構造体変数が初期値のままとなるため > 各フィールドの配列もまた、初期化されていない状態となります。 > > > 案4 > public unsafe struct pcKIROKU > { > public fixed byte KYOBI1[28]; > public byte KZokusei; > public byte IkisakiCd; > public fixed byte KTutatuNo[2]; > public fixed byte KTatuHkb[3]; > public fixed byte KSekobi[3]; > public fixed byte KSigyoKumi[11]; > public fixed byte KSigyoNo[2]; > public byte KKushoCd; > } > > > > やりたい事は2次元の構造体に読み込んだデータ(レコード)を入れて参照、更新したいのですが。 > 二次元なら、たとえば > Dim mcKIROKU(2, 3) As pcKIROKU > のような宣言になるでしょうね。 > > > データレコードの管理ならば、DataTable を使う手法もあります。 ありがとうございました。 おかげさまで解決しました。 |