11

Collection新しいクラスで VBA オブジェクトの機能を拡張し、このクラスを の継承にしようとしていますCollectionが、Implements Collectionステートメントで次のエラーが発生します。

Implements のインターフェイスが正しくありません: メソッドの名前にアンダースコアが含まれています。

何アンダースコア?! Add、、、およびはItem、のドキュメントにリストされている唯一のメソッドです。4 つすべてにアンダースコアがありません。RemoveCountCollection

EDIT:明確にするために、私は(このアプローチUniformCollectionに触発された、すべて同じタイプのメンバーのみを受け入れる)というクラスを作成しています。を実装して、 aが であり、他のオブジェクトのメソッドなどを呼び出すときに a の代わりに使用できるようにしたいと思います。 CollectionUniformCollection CollectionCollection

Add、Item などの委任メソッド/プロパティ、および動作するための NewEnum プロパティを作成する必要があることはわかっていますがFor Each、既に作成しています。

私の問題は、Implements Collectionステートメントが上記のエラーを私に与えることです。

おまけの質問:CountのメソッドまたはプロパティはCollection? ヘルプではこれをプロパティと呼んでいますが、VBA エディタのオブジェクト ブラウザでは関数、つまりメソッドと呼んでいます (フライング イエロー ボックス)。

4

4 に答える 4

8

VBA の実装の制限の 1 つに遭遇しています。名前にアンダースコアが含まれるパブリック メソッドまたはプロパティが他のクラスにある場合、別のクラスを実装することはできません。Collectionクラスにはもちろんあります_NewEnumが、アンダースコアがあると問題が発生します。

たとえばAddressClass、次のようなクラスを作成したとします。

Public Address_City As String

次に、別のクラスを作成しましたCustomerAddress

Implements AddressClass

Private Property Get ClassInterface_Address_City() As String
End Property

Private Property Let ClassInterface_Address_City(ByVal RHS As String)
End Property

コンパイルすると、「オブジェクト モジュールはインターフェイス 'AddressClass' の 'Address_City' を実装する必要があります」というエラーが表示されます。プロパティを に変更するAddressCityと、エラーがなくなります。

考えられる解決策:私の理解が正しければ、コレクション クラスを実装して、コレクションをパラメーターとして受け取るメソッドに新しいクラスを渡すことができます。これらの方法を変更することは可能ですか? 私の提案は、独自のコレクション クラスを作成し、MyCollection代わりにそれを実装することです。つまりUniformMyCollection、アンダースコアの問題を完全に回避できます。

についてはCount、いつでもヘルプ テキストよりもオブジェクト ブラウザを信頼します。一方、独自のコレクション クラスを作成する場合は、どちらを選択してもかまいません。

于 2011-11-11T07:24:07.037 に答える
6

VBA には、実装できるクラスに多くの制限があります。NewEnum は Collection をつまずかせていますが、たとえそうでなかったとしても、そのクラスにはそれをつまずかせる何かが他にある可能性が非常に高いです。最初に見つかった問題を報告すると思います。

Collection にはプロパティとメソッドがほとんどないため、それらを書き直すだけです。

Private mcolParts As Collection

Public Sub Add(clsPart As CPart)
    mcolParts.Add clsPart, CStr(clsPart.PartID)
End Sub

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

Public Property Get Item(vItm As Variant) As CPart
    Set Item = mcolParts.Item(vItm)
End Property

Public Sub Remove(vIndex As Variant)
    mcolParts.Remove vIndex
End Sub

OB がメソッドを表示する理由がわかりません (私には緑色のボックスのように見えます)。私の考えでは、メソッドは複数のプロパティを変更するか、クラス外の何かとやり取りします。それ以外はすべてプロパティです。Count プロパティと Index プロパティの両方を呼び出します。

于 2011-04-21T21:34:43.720 に答える
4

ディック・クスレイカがそのほとんどを持っていますFor Eachが、カスタムクラスで使用する場合は、次のものも必要です。

'--- required additional property that allow to enumerate the collection with For Each
Public Property Get NewEnum() As IUnknown
    Set NewEnum = m_ColParts.[_NewEnum]
End Property

これは、私のお気に入り(これまたはこれ)で見つけたリンクのどちらでも説明されていませんが、どちらも読む価値があります。NewEnumについて説明しているサイトを見つけたら、編集して追加します。

編集

これらのリンクはどちらも私が探していたものではありませんが、どちらもNewEnumプロパティ(追加する必要のある少し余分なブードゥーを含む)について説明しています。

ここここ

これらは両方ともExcelについて説明していますが、VBAは他のOfficeアプリケーションでも同じです(「属性」を取得するためのエクスポート->テキスト編集->インポートプロセスの必要性を含む)。

于 2011-04-21T23:27:41.313 に答える
3

「NewEnum」に関するRolandTumbleのメモ:

Access 2003での私自身の経験では、「ForEach」は次の行を含むコードをインポートすることで正常に機能します

Attribute NewEnum.VB_UserMemId = -4

...しかし、ファイルを「/逆コンパイル」した後(コマンドラインスイッチ)、その行は削除され(エクスポート時に確認され)、「ForEach」は機能しません。

残念ながら、「圧縮と修復」で問題が解決しない場合は、「/Decompile」を使用する必要があります。

于 2012-10-20T23:22:57.300 に答える