C# 什么是私有接口?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/792908/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-05 01:19:31  来源:igfitidea点击:

What is a private interface?

c#

提问by RichardOD

In an interview a while ago for a .NET position the interviewer asked me "what would you use a private interface for?".

在不久前的一次 .NET 职位面试中,面试官问我“你会使用私有接口做什么?”。

I asked him did he mean the difference between implicit vs explicit interface implementation to which he answered no.

我问他他的意思是隐式和显式接口实现之间的区别,他回答没有。

So I'm wondering:

所以我想知道:

  1. What he meant?
  2. What you would use a private interface for?
  1. 他是什么意思?
  2. 您将使用私有接口做什么?

采纳答案by ShuggyCoUk

An interface could be private within another class

一个接口在另一个类中可以是私有的

public class MyClass
{
    private interface IFoo
    {
        int MyProp { get; }
    }

    private class Foo : IFoo
    {
        public int MyProp { get; set; }
    }

    public static void Main(string[] args)
    {
        IFoo foo = new Foo();
        return foo.MyProp;
    }
}

in terms of utility it simply hides from other code, even within the same assembly, that said interface exists. The utility of this is not terribly high in my opinion.

就实用性而言,它只是对其他代码隐藏,即使在同一个程序集中,该接口存在。在我看来,它的实用性并不是很高。

Explicit interface implementationis a different matter, has some very useful cases (especially when working with generics and older non generic interfaces) but I would not term it 'private interfaces' and would not say that the term is commonly used in that manner.

显式接口实现是另一回事,有一些非常有用的情况(尤其是在使用泛型和较旧的非泛型接口时),但我不会将其称为“私有接口”,也不会说该术语通常以这种方式使用。

Using the two techniques together you can do:

结合使用这两种技术,您可以:

public class MyClass
{
    private interface IFoo
    {
        int MyProp { get; }
    }

    public class Foo : IFoo
    {
        int IFoo.MyProp { get; set; }
    }

    public static void Main(string[] args)
    {
        IFoo foo = new Foo();
        return foo.MyProp;
    }
}

public class HiddenFromMe
{
    public static void Main(string[] args)
    {
        MyClass.Foo foo = new MyClass.Foo();
        return foo.MyProp; // fails to compile
    }
}

This allows you to expose the nested classes in some fashion while allowing the parent class to invoke methods on them that the outside world cannot. This is a potentially useful case but is not something I would wish to use very often. Certainly it's use in an interview smacks of being a boundary case the interviewer is using because they've seen it and though it was 'interesting'

这允许您以某种方式公开嵌套类,同时允许父类调用外部世界无调用的方。这是一个潜在有用的案例,但不是我希望经常使用的。当然,它在面试中的使用有点像面试官使用的边界案例,因为他们已经看到了它,尽管它很“有趣”

回答by Mark Dickinson

From this link.

这个链接

Private Interface Inheritance

Historically, languages have permitted private inheritance. In C++, you can inherit from a type without being polymorphically compatible with that type. It's just a convenient way to reuse an implementation. In the CTS, you cannot do private implementation inheritance. But you can use private interface inheritance.

Private interface inheritance is really just a way to hide methods from a type's public API. They are compiled into private methods but are actually accessible through a type's interface map. In other words, they can only be called through a reference typed as the interface on which the method is defined. An example will make this easier to understand:

class PrivateImplementer : IFoo
{
   void IFoo.Foo()
   {
       Console.WriteLine("PrivateImplementer::IFoo.Foo");
   }
}

In this case, PrivateImplementeris publicly known to implement IFoo. Thus, an instance can be treated polymorphically as an instance of IFoo. But you cannot actually call Foo on it unless you do treat it as an IFoo. This code demonstrates this:

PrivateImplementer p = new PrivateImplementer();
p.Foo(); // This line will fail to compile
IFoo f = p;
f.Foo();

You can select individual methods of an interface to implement privately. For instance, if PrivateImplementerimplemented IFooBar, it might choose to implement Foo privately, but Bar publicly using the ordinary syntax.

In practice, there aren't many common cases where you would use private implementation. The System.Collections.Genericlibrary uses this approach to secretly implement all of the legacy System.Collections weakly typed interfaces. This makes backwards compatibility "just work," for example passing an instance of List<T>to a method that expects an IListwill work just fine. In this specific example, cluttering the new type APIs would have been a pity (there are quite a few methods necessary for the weakly typed interoperability).

私有接口继承

历史上,语言允许私有继承。在 C++ 中,您可以从一个类型继承而无需与该类型多态兼容。这只是一种重用实现的便捷方式。在 CTS 中,您不能进行私有实现继承。但是您可以使用私有接口继承。

私有接口继承实际上只是一种从类型的公共 API 中隐藏方的方。它们被编译成私有方,但实际上可以通过类型的接口映射访问。换句话说,它们只能通过类型化为定义方的接口的引用来调用。一个例子将使这更容易理解:

class PrivateImplementer : IFoo
{
   void IFoo.Foo()
   {
       Console.WriteLine("PrivateImplementer::IFoo.Foo");
   }
}

在这种情况下,PrivateImplementer是众所周知的实施IFoo. 因此,可以多态地将实例视为 的实例IFoo。但是您实际上不能在其上调用 Foo ,除非您确实将其视为IFoo. 此代码演示了这一点:

PrivateImplementer p = new PrivateImplementer();
p.Foo(); // This line will fail to compile
IFoo f = p;
f.Foo();

您可以选择接口的各个方来私有实现。例如,如果PrivateImplementer实现了IFooBar,它可能会选择私下实现 Foo,而 Bar 使用普通语公开实现。

在实践中,使用私有实现的常见情况并不多。该System.Collections.Generic库使用这种方秘密实现所有遗留的 System.Collections 弱类型接口。这使得向后兼容性“正常工作”,例如将 的实例传递List<T>给期望 anIList可以正常工作的方。在这个特定的例子中,将新类型的 API 弄得一团糟是很遗憾的(弱类型互操作性需要很多方)。

"No," is a pretty poor answer if he was looking to find out what you knew. Sounds like someone who just wants to show how much they know.

“不,”如果他想找出你所知道的,这是一个非常糟糕的回答。听起来像是一个只想展示他们知道多少的人。

回答by Gerrie Schenck

Just like an inner class (which is also private) you can use a private interface in an existing class.

就像内部类(也是私有的)一样,您可以在现有类中使用私有接口。

回答by majkinetor

I googled around a bit and found thisarticle explaining how private interfaces can be used to provide different interfaces to different clients. This is C++ story.

我搜索了一下,发现这篇文章解释了如何使用私有接口为不同的客户端提供不同的接口。这是 C++ 的故事。

I don't think this can be applied to C# tho, because the same effect IMO can be achieved with explicit interfaces and clients that cast host to appropriate interface.

我不认为这可以应用于 C# tho,因为 IMO 可以通过显式接口和将主机转换为适当接口的客户端来实现相同的效果。

Maybe somebody else can see something I missed there....

也许其他人可以看到我在那里错过的东西......

I also found this at MSDN:

我也在MSDN 上找到了这个:

Interface methods have public accessibility, which cannot be changed by the implementing type. An internal interface creates a contract that is not intended to be implemented outside the assembly that defines the interface. A public type that implements a method of an internal interface using the virtual modifier allows the method to be overridden by a derived type that is outside the assembly. If a second type in the defining assembly calls the method and expects an internal-only contract, behavior might be compromised when, instead, the overridden method in the outside assembly is executed. This creates a security vulnerability.

接口方具有公共可访问性,不能由实现类型更改。内部接口创建了一个不打算在定义接口的程序集之外实现的契约。使用 virtual 修饰符实现内部接口的方的公共类型允许该方被程序集外部的派生类型覆盖。如果定义程序集中的第二种类型调用该方并期望仅内部协定,则当执行外部程序集中的重写方时,行为可能会受到损害。这会造成安全漏洞。

回答by max_cn

ShuggyCoUk gives good answer but with such comment

ShuggyCoUk 给出了很好的答案,但有这样的评论

This is a potentially useful case but is not something I would wish to use very often. Certainly it's use in an interview smacks of being a boundary case the interviewer is using because they've seen it and though it was 'interesting'

这是一个潜在有用的案例,但不是我希望经常使用的。当然,它在面试中的使用有点像面试官使用的边界案例,因为他们已经看到了它,尽管它很“有趣”

I, must to say, it's definitely not ability for only smart interviewers.

我,必须说,这绝对不是只有聪明的面试官才有的能力。

Here is Realization of Full State Machine (FSM) with inheritance and unitest support, which is good example of private/protected interfaces usage.

这是具有继承和统一支持的完整状态机 (FSM) 的实现,这是私有/受保护接口使用的一个很好的例子。

It was an answer on questions What is the C# equivalent of friend?and Why does C# not provide the C++ style 'friend' keyword?and, in fact, on your question too.

这是一个问题的答案什么是 C# 相当于朋友?为什么C#不提供C ++风格的“朋友”关键字?事实上,关于你的问题也是如此。