2011-08-09 10 views
14

アクセシビリティに関する初心者セッション用のデモコードをいくつか設定しています。派生クラスから内部保護されたプロパティにアクセスできることがわかりました。私は何が欠けていますか?他のアセンブリから依然としてアクセス可能な内部保護プロパティ

アセンブリ1

namespace Accessibility 
{ 
    class Program 
    { 
     static void Main(string[] args) 
     { 
      ExampleClass c = new ExampleClass(); 
      c.Go(); 
      //c.Prop1 = 10; 
     } 
    } 

    class ExampleClass : DerivedClass 
    { 
     public void Go() 
     { 
      this.Prop1 = 10; 
      this.Prop2 = 10; 
      //this.Prop3 = 10; //Doesn't work 
      //this.Prop4 = 10; //Doesn't work 
      this.Prop5 = 10; //why does this work?! 

      this.DoSomething(); 
     } 
    } 
} 

アセンブリ2

namespace Accessibility.Models 
{ 
    public class BaseClass 
    { 
     public int Prop1 { get; set; } 
     protected int Prop2 { get; set; } 
     private int Prop3 { get; set; } 

     internal int Prop4 { get; set; } 
     internal protected int Prop5 { get; set; } 
     //internal public int Prop6 { get; set; } //Invalid 
     //internal private int Prop7 { get; set; } //Invalid 

     public BaseClass() 
     { 
      this.Prop3 = 27; 
     } 
    } 

    public class DerivedClass : BaseClass 
    { 
     public void DoSomething() 
     { 
      this.Prop1 = 10; 
      this.Prop2 = 10; 
      //this.Prop3 = 10; //Doesn't work 
      this.Prop4 = 10; 
      this.Prop5 = 10; 

      PropertyInfo Prop3pi = typeof(DerivedClass).GetProperty("Prop3", BindingFlags.Instance | BindingFlags.NonPublic); 
      int value = (int)Prop3pi.GetValue(this, null); 
     } 
    } 
} 

私はProp5に値を設定することができますExampleClass.Goで注意してください。どうして?これは内部が保護されたとしてマークされていますが、それはinternal protectedが動作するように意図された方法ですので、私は(内部としてマーク)Prop4上の値

+16

* internal * OR * protected *ですので、 ANDではありません。 –

+1

-1:明らかに、単純なGoogle検索でこの質問に回答していたでしょう... –

+1

私はそれがORであったとは思わなかった –

答えて

20

internal protectedは、「アセンブリまたは継承されたクラスへの内部」を意味します。あなたが保護された内部部材とのpublicクラス、異なるアセンブリ内のそのタイプを継承する別のクラスを持っているのであれば、はい、でき未だにためprotected修飾子のそれにアクセス:

が保護された内部

タイプかアセンブリは、アセンブリが宣言されている任意のコード(別のアセンブリの派生クラス内のまたは)からアクセスできます。別のアセンブリからのアクセスは、保護された内部要素が宣言されているクラスから派生したクラス宣言内で行われなければならず、派生クラス型のインスタンスを通じて行わなければなりません。

リファレンス:http://msdn.microsoft.com/en-us/library/ms173121.aspx

これはC#言語の制限があります。 CLRは、「内部AND保護」という概念をサポートしています。独自のILを放出していた場合は、MethodAttributes.FamANDAssem列挙型の証拠があります。 本当ににこの機能が必要だった場合は、Mono.CecilなどのIL後処理を実行できます。なぜC#言語がこれを公開しないのかは、推測にすぎません。ほとんど必要ありません。

6

を設定することはできません。継承ツリー(protected部分)または同じアセンブリ(internal部分)の子のどちらにもアクセスできます - Access Modifiers on MSDNを参照してください。

ExampleClassは、BaseClassの継承ツリーにあり、Prop5を定義しています。アクセスはprotectedのおかげです。同じアセンブリ内のみ派生型又は種類がそのメンバーにアクセスすることができる - クラスメンバは、内部保護マークすることができ、保護された内部のキーワードを組み合わせることにより

+0

私は簡単な説明が好きです。 –

4

This MSDN articleは、すべてのご質問にお答えします。

+0

これは、制限されたキーワードに限定されているわけではありませんか? –

+0

これは正しいです。 protected internalは、派生型(protected)とアセンブリ(internal)の両方がアクセスできることを意味します。これは内部修飾子にのみ適用されます。あなたは他のものを組み合わせることはできません。 –

3

protectedキーワードはメンバアクセス修飾子です。保護されたメンバは、それが宣言されたクラス内からアクセス可能であり、このメンバを宣言したクラスから派生した任意のクラス内からアクセス可能です。保護された内部のキーワードを組み合わせることにより

http://msdn.microsoft.com/en-us/library/bcd5672a(v=vs.71).aspx

は、クラスメンバがマーク内部を保護することができる - だけ派生型またはタイプを同じアセンブリ内にそのメンバーにアクセスすることができます。

http://msdn.microsoft.com/en-us/library/ms173121(v=vs.80).aspx

2

Protectedそれが唯一の子孫のクラスによって共有されていることを意味し、唯一privateは、それが他の誰かがアクセスすることができないことを意味します。

編集:Hansのコメントはあなたの質問をもう少し明確にします。そのような修飾語を組み合わせると、排他的ではなく包括的に組み合わされます。それはすべての方法でアクセスしますinternalまたはprotectedすることができます。

0

最新の回答ですが、私は同じ問題を抱えています。結局私は部分的な解決策を考え出した。

internal Int MyInt 
    { 
     get; 
     protected set; 
    } 

これはアセンブリ内ではまだ表示されていますが、少なくとも継承クラスのみが実際に変更することができます。私の望むもので十分です。

関連する問題