您是否曾见过合理使用受保护的内部访问修饰符的设计?

时间:2010-10-06 18:56:47

标签: c# access-modifiers

我没有,但我不说没有。

所有阅读此内容的C#开发人员可能都知道内部受保护的内容以及何时使用它。我的问题很简单:您是否真的使用过它,或者使用受保护的内部访问修饰符处理成功设计的项目?如果是的话,请分享您的知识并发布好的样本,我终于可以理解这个棘手的修饰符的巧妙使用。

//我认为这不是主观的,我实际上是在寻求答案; - )

6 个答案:

答案 0 :(得分:6)

是的,在继承情况下,只要允许虚拟或抽象类成员以“友好”/可信方式被同一程序集(内部)中的其他类直接访问,而且该成员可以通过派生来覆盖外部程序集中的类(通过保护)。

此组合修饰符允许程序集完全信任其自己的内容和内部用法(这不是异常),同时将其中一些成员公开给其他程序集的正常继承派生模型。

没有一个修饰符可以做到这一点。

或者考虑相反的情况:

  • 如果使用 protected ,则同一程序集中的其他类无法访问该成员。

  • 如果使用内部,则派生类(在其他程序集中)无法覆盖该方法。

Assembly1.dll

// ------ Assembly file 1 .dll --------

// Allow my friends (internal) and derived classes (protected) to do this. 
public class A {
    internal protected virtual void YoBusiness() {
        //do something
    }
}


class B { // not a derived class - just composites an instance of A
    public B() {
        A a = new A();
        a.YoBusiness(); // Thanks friend for the access! 
    }
}

Assembly2.dll

// ------ Assembly file 2 .dll --------

class C : A {  // derived across assemblies
    protected override void YoBusiness() {
        // Hey thanks other guy, I can provide a new implementation. 
    }
}

答案 1 :(得分:6)

我相信你可以想到一些例子,但是在C#开发的五年里,我没有看到它的好例子。 John K的例子很好地说明了修饰符的用途,但我认为导致这种情况的要求是有问题的。在John K的例子中,该类在程序集中具有“友好”访问权限,并且通常这是麻烦,因为这些类可能是“询问”而不是“告诉”(编程不礼貌,最好告诉而不是问)。在什么情况下你有一个有用的可扩展类,朋友可以调用方法,但其他人不能?

另一种用途是用于测试访问(IE希望它受到保护,但内部因此您的程序集级别测试可以调用它)。这也是一个麻烦的情况 - 当你将内容暴露在内部进行测试时,我认为这是依赖注入通常可以处理的设计气味。

答案 2 :(得分:1)

所有protectedinternal成员都会增加复杂性,耦合并因此降低抽象完整性。你可能会考虑实现一些内部或受保护的方法,但一般使用内部或受保护的字段是非常糟糕的主意。受保护/内部字段“打开”各种类的抽象实现,并使未来的修改高度复杂化。

我不喜欢像“从不”或“不要”这样的词作为设计指南,但我们绝对应该至少使用“避免“建议作为通用设计指南。

答案 3 :(得分:0)

  

你真的用过吗

是的,以及InternalsVisibleTo进行单元测试。

答案 4 :(得分:0)

对于想要继承你的类型的人来说,这只是一个意思,因为他们不和你在同一家公司工作。 ;-)

但是,严重的是,这个问题仅适用于内部......我们知道你为什么要使用受保护的,对吗?那么,为什么内部?可能只有当您知道您的类型访问某些仅在同一程序集中可用的资源时。无论是实际资源,还是您不想与世界分享的其他类型。

答案 5 :(得分:0)

我实际上必须在今天的职业生涯中第一次使用它!我有一个带有baseclases的插件架构,插件只能通过facade类暴露。限制以便插件只能通过faqade调用的唯一方法是使其受到内部保护,因为覆盖它的插件位于其他程序集中,而faqade层与基类相同

我有点担心选择会回来咬我,不过如此,我很想让公开公开