ジェネリッククラスの静的変数の罠にはまりかけたのでメモ。
ジェネリッククラスとはなんぞ?って話は山程ある解説サイト様にお任せするとして、オブジェクト指向言語における静的変数は、たとえ別のインスタンスであっても共有できちゃうぞって認識でした。
class ClassA
{
protected static string Name = "ClassA";
}
class ClassB : ClassA
{
}
class ClassC : ClassA
{
}
こういったクラス関係で、ClassBのインスタンスからNameを変更すると、ClassCのインスタンスから見えるNameも変更されちゃうよってことですね。
でもジェネリッククラスになると注意が必要です。
class ClassA<T>
{
protected static string Name = "ClassA";
}
class ClassB<int> : ClassA<int>
{
}
class ClassC<string> : ClassA<string>
{
}
class ClassD<string> : ClassA<string>
{
}
こういったクラス関係だと、ClassBのインスタンスからNameを変更しても、ClassC,ClassDのインスタンスから見えるNameは変更されません。
でもClassCのインスタンスからNameを変更すると、ClassDのインスタンスから見えるNameは変更されます。
各B~Dクラスから見た親クラスの型は、ClassA<int>とClassA<string>になり、この2つは別の型。
だから静的変数の確保領域も別になる。ってことらしいです。
さて、じゃあClassBとClassCでNameを共有したい時にどうするか。
そしてClassAの中でNameを変更する時にどうするか。
型が一致していれば共有されるので、その型を作っちまいましょう。
何でもいいんですが、
コレはジェネリッククラスの静的メンバにアクセスしてるんだよー!
ってわかった方が気持ちがいいので、それ用にクラスを作ってしまいました。
sealed class AccessGenericStaticMember{
}
一応処理をしないクラスよって意味でsealedをつけてます。
後はクラスA~Dまで共通して使いたければ、NameではなくClassA<AccessGenericStaticMember>.Nameにアクセスするようにします。
たったそれだけのことなんですがね。
他にもニッチなIT関連要素をまとめていますので、よければ一覧記事もご覧ください。