以前のεπιστημηさんのVB嫌い[2]というエントリーで
VBの引数付きプロパティとC#のインデクサを比較する話がありました。
Delphiにも配列プロパティというのがありまして、VBの引数付きプロパティと
同じような使い方ができます。(のはず。VB知らないので間違ってたらご指摘ください。)
type
TAnimals = class(TObject)
private
function GetDog(Index: Integer): TDog;
procedure SetDog(Index: Integer; Value: TDog);
function GetCat(Index: String): TCat;
public
//ReadWriteプロパティ
property Dogs[Index: Integer]: TDog read GetDog write SetDog;
//ReadOnlyプロパティ
property Cats[Index: String]: TCat read GetCat;
end;
C#のインデクサと比較しての便利さは、やはりgetterとsetterのメソッドを定義するだけで
使えるところ。
そこで、C#2.0のジェネリックを使って、以下のようなユーティリティクラスを作ってみました。
public delegate V ArrayProperty1Get<V, K1>(K1 key1);
public delegate void ArrayProperty1Set<V, K1>(K1 key1, V value);
public class ReadOnlyArrayProperty1<V, K1>
{
public ReadOnlyArrayProperty1(
ArrayProperty1Get<V, K1> getMethod)
{
this.getMethod = getMethod;
}
private ArrayProperty1Get<V, K1> getMethod;
public V this[K1 key1]
{
get
{
return getMethod(key1);
}
}
}
public class ReadWriteArrayProperty1<V, K1>
{
public ReadWriteArrayProperty1(
ArrayProperty1Get<V, K1> getMethod,
ArrayProperty1Set<V, K1> setMethod)
{
this.getMethod = getMethod;
this.setMethod = setMethod;
}
private ArrayProperty1Get<V, K1> getMethod;
private ArrayProperty1Set<V, K1> setMethod;
public V this[K1 key1]
{
get
{
return getMethod(key1);
}
set
{
setMethod(key1, value);
}
}
}
これを使うと
public class Animals
{
public Animals()
{
Dogs = new ReadWriteArrayProperty1<Dog, int>(GetDog, SetDog);
Cats = new ReadOnlyArrayProperty1<Cat, string>(GetCat);
}
private Dog GetDog(int index)
{
//
}
private void SetDog(int index, Dog value)
{
//
}
private Cat GetCat(string index)
{
//
}
public ReadWriteArrayProperty1<Dog, int> Dogs;
public ReadOnlyArrayProperty1<Cat, string> Cats;
}
class Program
{
static void Main(string[] args)
{
Animals animals = new Animals();
animals.Dogs[0] = new Dog("パトラッシュ");
animals.Dogs[1] = new Dog("ラッシー");
animals.Cats["ABC"] = new Cat("たま"); //コンパイルエラー
}
}
みたいなことができます。
「インデクスが2つ以上ある場合はど~するんや」と突っ込まれそうですが
その場合はK2、K3、…と型パラメータを増やしたバージョンを追加します。
私の経験上、インデクスが4つ以上もあるような配列プロパティには、自社開発の
アプリも含めて出合った記憶がありません。