Object 型

 これまで詳しく触れてきませんでしたが、VB 組み込みのデータ型に、「Object」という型があります。

これは、オブジェクトのインスタンスを格納できるデータ型(つまり、クラスのようなもの)ですが、特別なのは、すべてのクラス型のインスタンスを受け入れることができるということです。

    Dim sprApple As Sprite
    Dim objApple As Object
    
    Set sprApple = New Sprite
    Set objApple = New Sprite
    
    Call sprApple.LoadImage(IMGNAME_APPLE)
    Call objApple.LoadImage(IMGNAME_APPLE)

sprApple も、objApple も、どちらも同じ Sprite 型のオブジェクトとして扱うことができます。

いわば、オブジェクト型に対する Variant 型です。
As Object として宣言されたオブジェクト変数には、すべてのオブジェクトインスタンスを格納することができます。

問題点

 しかし、Variant 型と同じように、問題点もいくつかあります。

「何でも入ってしまう箱」は、何でも入ってしまうゆえの危険性も持っています。
たとえば、Form のインスタンスを入れたかと思えば、次に PictureBox のインスタンスを入れたりすることも可能です。

プロパティやメソッドの呼び出しの際には、格納されているインスタンスのクラスがそのプロパティ・メソッドを持っていることが絶対条件になります。

Object 型の変数は、宣言された時点ではクラスの情報を持っていません。格納されるインスタンスがどんなプロパティ・メソッド・イベントを持っているのかわからないのです。(コードエディタの補完機能も働きません。)

事前バインディングと実行時バインディング

 Object 型で宣言されたオブジェクト変数には、本当に実行時まで何が入るのかわかりません。

そのため、(本来ならコンパイル時に型が決定されるべき変数の型が決定されないため、)実行時に型設定の作業が行われることになり、一般的に、実行速度に影響します。

これは「実行時バインディング」と呼ばれ、手軽さと引き替えに、実行速度低下と危険性のリスクを負います。

逆に、正しく型が定義されたオブジェクト変数は、コンパイル時にオブジェクトの型設定が行われるため、実行時バインディングよりも高速に処理できます。これは「事前バインディング」と呼ばれます。指定された型以外の代入はできず、他の型のインスタンスを代入しようとすると、エラーになります。

世間では、事前バインディングを「アーリーバインディング」、実行時バインディングを「レイトバインディング」と呼ぶこともあります。

使い所

 これらの問題やクラスの目的・意図から、できる限りオブジェクト変数の型は明確に指定するようにします。

実際には、変数として Object 型を使うことはほとんどありません。
Object 型や Variant 型が使用されるのは、プロシージャの引数などです。

引数に 2 種類以上のオブジェクトのいずれかを選択要求する場合などには都合が良いのです。(クラスの種類を気にしなくてもよい。)

Private Function CheckVerifyMessage(ByRef SelectedItem As Object) As Boolean

    If SelectedItem Is Nothing Then ...
    If TypeOf SelectedItem Is Sword Then ...
    If TypeOf SelectedItem Is Armor Then ...

End Function

しかし、VB のクラスモジュールには、As Object という広い定義ではなく、クラスを狭いカテゴリで区別し種類分けする「ポリモーフィズム」という機能が備わっています。

やはり、Variant 型と同じく、あまり使い所はないのかもしれません。

補足情報

タイプライブラリ
クラスのインターフェイスに関する情報が記述されたファイル。
ActiveX コンポーネントファイルに含まれる。
COM を C++ 以外の言語で利用するための技術のひとつ。
(ActiveX コンポーネントをコンパイルしたら自動的に作成されている。)

※Object 型の実体は、Long 型と同じ整数値です。
オブジェクトインスタンスへのポインタが格納されています。
オブジェクトでない型は格納しないので、Variant 型のようにメモリを沢山とってしまう、ということはありません。

※Variant 型にオブジェクトインスタンスを格納することもできますが、オブジェクトだけを格納することが決まっている場合は、As Object とします。

2000年 9月17日(日) 更新