コレクションのItemについて

解決


るーちゃん  2006-08-05 03:40:06  No: 132659

いつもお世話になってます。
長文です。すいません。

開発環境
VB6.0です

今回の質問は、不具合の解決方法では
なくて、どうしてこのような動作ができる
のか理屈が分からないのです。
申し訳ありませんが、お時間を頂けません
でしょうか。

VBに備わっているCollectionを使って、
自作のコレクションmPrimArrayを作り、
これまた自作したクラス(CPrimitiveArray)で
隠蔽しました。mPrimArrayのメソッド等を
公開したつもりです。

↓CPrimitiveArray.cls  ---------------

Private mPrimArray as Collection

Private Sub Class_Initialize()
    Set mPrimArray = New Collection
End Sub

Private Sub Class_Terminate()
Dim iCnt As Long
    For iCnt = 1 To mPrimArray.Count
        mPrimArray.Remove 1
    Next iCnt
    Set mPrimArray = Nothing
End Sub

Public Sub Add(pName As String, pObj As String)
Dim mPrim   As CPrimitive
    Set mPrim = New CPrimitive

    mPrim.pID = mPrimArray.Count
    mPrim.pName = pName
    mPrim.pObj = pObj
    mPrimArray.Add Item:=mPrim, Key:=pName
    Set mPrim = Nothing
End Sub

Public Sub Remove(Index As Variant)
    mPrimArray.Remove Index
End Sub

Public Property Get Count() As Long
    Count = mPrimArray.Count
End Property

Public Property Get Item(Index As Variant) As CPrimitive
    Set Item = mPrimArray(Index)
End Property

↑-------------------------------------

mPrimArrayコレクションには、別クラスで作成した、
データを保持するだけのクラスのインスタンスが
格納されます(CPrimitive)。

↓CPrimitive.cls  -------------------------------

Private Type tElem      '1単位データ
    primID  As Long     'ID
    primName As String  '名称
    primObj As String   '実体
End Type
Private mElem As tElem

Public Property Get pID() As Long
    pID = mElem.primID
End Property
Public Property Let pID(Value As Long)
    mElem.primID = Value
End Property

Public Property Get pName() As String
    pName = mElem.primName
End Property
Public Property Let pName(Value As String)
    mElem.primName = Value
End Property

Public Property Get pObj() As String
    pObj = mElem.primObj
End Property
Public Property Let pObj(Value As String)
    mElem.primObj = Value
End Property
↑-----------------------------------------------

で、フォームの側では、CPrimitiveArrayを宣言して、
適当に値を追加したり、内容を書き換えたりします。

↓Form1.frm -------------------------------------
Private Sub Command1_Click()
Dim a As CPrimitiveArray

    Set a = New CPrimitiveArray
    
①  MsgBox "セット前の配列の個数:" & a.Count
    a.Add "test", "aaaa"
②  MsgBox "セット後の配列の個数:" & a.Count
③  MsgBox "test:" & a.Item("test").pObj
→  a.Item("test").pObj = "fdfd"
④  MsgBox "test:" & a.Item("test").pObj
    Set a = Nothing

End Sub
↑-----------------------------------------------

質問は、Itemについてです。

Command1_Clickのほうで、a.Item("test").pObj は、
参照はいいとして、代入ができてしまいます(→印)。
CPrimitiveArrayでの実装では、Getしか記述してません
(参照専用のはずだと考えてます...)
代入ができてしまうのは何故ですか?

もしや、たまたま動いてるだけとか。。

※印のメッセージは以下になります。
① 0
② 1
③ test:aaaa
④ test:fdfd

(ちなみに、参照と代入は両方できるのを
 目標としてますので、動作はOKなんです)


KG  2006-08-05 04:26:21  No: 132660

CPrimitiveではpObjへの代入は許可されていますよね。

ならItemがCPrimitiveなのでpObjへ代入できるのは自然かと|=_=;

#Item自体は代入できないでしょうけど。


るーちゃん  2006-08-07 17:57:15  No: 132661

KG殿

コメントありがとうございます。

>pObjへの代入は許可
はい。たしかに代入も許可した実装にはしてます。
CPrimitiveArrayで、Item(CPrimitive)は参照のみ
と書いてあってもCPrimitiveに従ってしまう
ものなんですね〜


るーちゃん  2006-08-09 19:01:58  No: 132662

[解決]入れ忘れました


Geo=TK3  2006-08-09 20:52:33  No: 132663

>CPrimitiveArrayで、Item(CPrimitive)は参照のみ
>と書いてあってもCPrimitiveに従ってしまう
>ものなんですね〜

なんか誤解があるような?
この文章からは CPrimitiveArray の設定を CPrimitive が上書き
している印象を受けますが、そうお考えでしょうか?


るーちゃん  2006-08-09 22:55:42  No: 132664

>上書き

とは考えていません。
逆にお尋ねしますが、上書きということは可能なんですか?

CPrimitiveArrayはCprimitiveのインスタンスを提供
するだけで、特にCPrimitiveArrayが参照のみであっても(
こういう言い方は誤解を招くのですかね。。他に良い
言い方知らなくて。。)

CprimitiveにLetがある以上は、代入ができてしまいますよ。
ということだと解釈してます。


Geo=TK3  2006-08-10 03:17:05  No: 132665

なるほど、大変失礼いたしました。

> 逆にお尋ねしますが、上書きということは可能なんですか?
いや、出来ません。
だからこそ先の質問させていただいた訳で...

>こういう言い方は誤解を招くのですかね。。他に良い
>言い方知らなくて。。)
今回は私の解釈に原因がありそうですが、この手の説明は確かに
言葉に困りますね (^^;; 。


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




  


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