什么是C#访问修饰符,它们如何比较?有一个像样的视觉图?

时间:2015-12-09 17:29:18

标签: c# access-modifiers

研究:我已经阅读了提供定义的MSDN C# Access Modifiers reference,但很少有例子。这些定义是正确的,但如果它们在图表中以可视方式呈现则更容易理解。搜索SO我发现了几个问题,讨论了修饰符的特殊情况,或者将一个修饰符与另一个修饰符进行比较,但不是所有修饰符,而不是视觉上。我还在网上搜索了“C#Access Modifier Diagrams”,并且能够找到this快速参考,其中包含一些示例和图表,但并不像我希望的那样清晰。我无法找到这个信息的全部来源。

问题 我想找到一个C#Access Modifiers的一个指南,它使用定义,代码示例和视觉辅助工具(如图表)显示以下内容。

  • C#中有哪些不同的访问修饰符?
  • 每个修饰符的范围是什么以及它们如何比较?
  • 它们如何应用于内部类,外部类,继承类和非继承类?

1 个答案:

答案 0 :(得分:4)

根据MSDN C# Reference

在c#中有5个级别的访问修饰符。列出从最受限制到最低限制,它们如下:

  1. 私人
    • 访问仅限于包含类型。
  2. 受保护
    • 访问仅限于从包含类派生的包含类或类型。
  3. 内部
    • 访问仅限于当前程序集。
  4. 受保护的内部
    • 访问仅限于从包含类派生的当前程序集或类型。
  5. 公共
    • 访问不受限制。
  6. 我创建了下图,以直观地显示这些修饰符的范围,因为它影响多个程序集,类和派生类。

    在此图中,有5种不同颜色的访问修饰符分组。对于每个分组,如果使用相应的访问修饰符修改BaseClassMember或NestedClass,则只有该组中的类才能访问它。外面的课程没有。

    例如,如果将BaseClassMember修改为"受保护",则只有橙色受保护组中的类才能访问BaseClassMember。这些类是BaseClass,InternalInheritedClass和ExternalInheritedClass。此行之外的类无权访问BaseClassMember。

    Access Modifiers Diagram 测试代码

    <强> Assembly1

    namespace Assembly1
    {
        public class BaseClass
        {
            public int PublicMember;
            protected internal int ProtectedInternalMember;
            internal int InternalMember;
            protected int ProtectedMember;
            private int PrivateMember;
    
            public class PublicClass { }
            protected internal class ProtectedInternalClass { }
            internal class InternalClass { }
            protected class ProtectedClass { }
            private class PrivateClass { }
        }
    
        public class InternalClass
        {
            public InternalClass()
            {
                BaseClass class0Instance = new BaseClass();
                var publicMember = class0Instance.PublicMember;
                var protectedInternalMember = class0Instance.ProtectedInternalMember;
                var internalMember = class0Instance.InternalMember;
                var protectedMember = "not accessible";
                var privateMember = "not accessible";
    
                var publicClass = new BaseClass.PublicClass();
                var protectedInternalClass = new BaseClass.ProtectedInternalClass();
                var internalClass = new BaseClass.InternalClass();
                var protectedClass = "not accessible";
                var privateClass = "not accessible";
            }
        }
    
        public class InternalInheritedClass : BaseClass
        {
            public InternalInheritedClass()
            {
                var publicMember = this.PublicMember;
                var protectedInternalMember = this.ProtectedInternalMember;
                var internalMember = this.InternalMember;
                var protectedMember = this.ProtectedMember;
                var privateMember = "not accessible";
    
                var publicClass = new BaseClass.PublicClass();
                var protectedInternalClass = new BaseClass.ProtectedInternalClass();
                var internalClass = new BaseClass.InternalClass();
                var protectedClass = new BaseClass.ProtectedClass();
                var privateClass = "not accessible";
            }
        }
    }
    

    <强> Assembly2

    using Assembly1;
    namespace Assembly2
    {
        public class ExternalClass
        {
            public ExternalClass()
            {
                BaseClass class0Instance = new BaseClass();
                var publicMember = class0Instance.PublicMember;
                var protectedInternalMember = "not accessible";
                var internalMember = "not accessible";
                var protectedMember = "not accessible";
                var privateMember = "not accessible";
    
                var publicClass = new BaseClass.PublicClass();
                var protectedInternalClass = "not accessible";
                var internalClass = "not accessible";
                var protectedClass = "not accessible";
                var privateClass = "not accessible";
            }
        }
    
        public class ExternalInheritedClass : BaseClass
        {
            public ExternalInheritedClass()
            {
                var publicMember = this.PublicMember;
                var protectedInternalMember = this.ProtectedInternalMember;
                var internalMember = "not accessible";
                var protectedMember = this.ProtectedMember;
                var privateMember = "not accessible";
    
                var publicClass = new BaseClass.PublicClass();
                var protectedInternalClass = new BaseClass.ProtectedInternalClass();
                var internalClass = "not accessible";
                var protectedClass = new BaseClass.ProtectedClass();
                var privateClass = "not accessible";
            }
        }
    }