繁体   English   中英

如何从 C# 中的接口隐藏已实现属性的设置方法?

[英]How to hide set method of an implemented property from an interface in C#?

大家好...

如果我有以下界面:

interface IMyInterface
{
    int property { get; set; }
}

以及以下实现:

class MyClass : IMyInterface
{
// anything
}

如何从MyClass的实例中隐藏属性的set方法...换句话说,我不希望propertyset方法是公共的,这可能吗?

抽象 class 很容易做到:

abstract class IMyInterface
{
    int property { get; protected set; }
}

然后我只能在实现上述抽象 class 的 class 中set property ...

开始时界面中没有set 您仍然可以将其实现为private

你不能“隐藏”它,它是合同的一部分。 如果您不希望它成为合同的一部分,请不要定义它。

如果某些实现只实现接口的某些部分,则最好将接口细分为每个实现将完全实现或根本不实现的部分,然后定义继承它们所有常见组合的接口。 调整你的例子:

interface IMyReadableInterface
{
    int property { get; }
}
interface IMyFullInterface : IMyReadableInterface
{
    new int property { get; set; }
}

想要支持读写访问的类应该实现 IMyFullInterface; 那些只想支持读取访问的人应该只实现 IMyReadableInterface。 对于使用 C# 编写并隐式实现property的任一接口的实现,这种隔离不需要任何额外的工作。 在 VB 中实现property的代码,或在 C# 中显式实现property的代码,将必须定义property的两种实现——一种只读和一种读写,但这就是生活。 properties (I really don't understand why C# can't use a read-only and write-only property together as thought they were a read-write property, but it can't).请注意,虽然可以定义一个只有一个 setter 的IMyWritableInterface ,并且让IMyFullInterface继承IMyReadableInterfaceIMyWritableInterfaceIMyFullInterface仍然必须定义自己的读写属性,并且在使用显式实现时必须定义属性(我真的不明白为什么 C# 不能一起使用只读和只写属性,因为它们认为它们是读写属性,但它不能)。

如果您使用以下接口,则当通过该接口操作类时,set 方法将不可用:

interface IMyInterface
{ 
   int property { get; }
}

然后,您可以像这样实现 class:

class MyClass : IMyInterface
{
  int property { get; protected set; }
}

假设您需要 setter 作为接口的一部分,但由于某种原因,在特定实现者(在本例中为 MyClass)上使用它没有意义,您总是可以在 setter 中抛出异常(例如 InvalidOperationException) . 这不会在编译时保护您,只会在运行时保护您。 但这有点奇怪,因为在接口上运行的代码不知道是否允许调用 setter。

在某些情况下,您希望接口有一个set ,然后将其隐藏在一些具体的 class 中。

我相信下面的代码显示了我们想要完成的事情。 即实现隐藏了setter,但任何IMyInterface感知组件都可以访问它。

public static void Main()
{
    var myClass = new MyClass();
    myClass.Property = 123;                 // Error
    ((IMyInterface)myClass).Property = 123; // OK
}

它基本上与您在IDisposable.Dispose()中经常看到的模式相同,其中您有一个Explicit Interface Implementation 这是完整性的示例。

public interface IMyInterface
{
    int Property { get; set; }
}

public class MyClass : IMyInterface, IDisposable
{
    public int Property { get; private set; }

    int IMyInterface.Property
    {
        get => Property;
        set => Property = value;
    }
    
    void IDisposable.Dispose() {}
}

打字太多:(

C#在这里对我们没有多大帮助。 理想情况下,设置器可以有一个显式的接口实现:

// In C# 10 maybe we can do this instead:
public class MyFutureClass : IMyInterface
{
    public int Property { get; IMyInterface.set; }
}

请参阅此处C#功能建议。

接口中没有受保护或私有的,一切都是公共的。 您要么不定义任何集合,要么将其用作公共。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM