『究極のC#プログラミング』 Chapter9 プロパティとアクセシビリティ

プロパティのアクセシビリティオーバーロードの解決

class A
{
  private string s;
  public string Name
  {
    get { return s; }
    set { s = value; }
  }
}

class B : A
{
  private string s;
  protected new string Name // protected, newで隠蔽
  {
    get { return s; }
    set { s = value; }
  }
}

class Program
{
  static void Main(string[] args)
  {
    B b = new B();
    b.Name = "hoge";
    Console.WriteLine(b.Name); // クラスBのNameはprotectedなので、クラスAのNameが呼ばれる。
  }
}


このようなオーバーロードの解決は、プロパティのアクセス修飾子によって決まるのであり、
get/setのアクセス修飾子では決まらない。
だから、上のコードにおいて、クラスBを

class B : A
{
  private string s;
  public new string Name
  {
    protected get { return s; }
    set { s = value; }
  }
}

と定義した場合には、クラスBのNameプロパティが呼ばれることになる。
しかし、getにはprotectedがついているので、コンパイルエラーになってしまう。


プロパティのアクセシビリティよりも弱いアクセシビリティをget/setにつけることはできない。
例えば、protectedなプロパティのget/setのアクセシビリティをpublicにすることはできない。


インターフェースの実装により、プロパティを実装するとき、そのプロパティにアクセシビリティを指定できない。
インターフェースメンバーのアクセシビリティは、プログラマによって指定できないのである。
指定してしまうとコンパイルエラーになる。