为什么我可以更改 class 中接口中定义的 属性 的实现

Why can i change an implementation of property defined in interface in the class

我试图理解,如果我创建一个接口 ITest,它定义了一个 属性 版本,其中只有 getter。然后,当我在 Test class 中实现此接口时,我可以将 属性 的定义更改为 getter 和 setter。如何更改接口的实现,如下所示?

internal interface ITest
    {
         int MyProperty { get;}
        void changeValue();
    }




   public class Test : ITest
    {
        public int MyProperty
        {
            get;
            set;
        }

        public void changeValue()
        {
        }
    }

如果您想更改 class 中的值,您应该添加 private setter:

internal interface ITest
{
     int MyProperty { get;}
     void ChangeValue();
}

class MyClass : ITest
{
    public int MyProperty { get; private set; }

    public void ChangeValue()
    {
        MyProperty = 1;
    }
}

记住:

接口成员:

int Property { get; }

实施正确:

public int Property { get; private set;}

public int Property
{ 
    get
    { 
        return 1;
    }
}

您不能更改接口成员的行为。这是class必须遵守的契约。

如果你正在做类似

ITest test = new Test();

您将无法公开访问 setter。如果您只想私下访问 setter,您可以使用:

public class Test : ITest
{
    public int MyProperty
    {
        get;
        private set;
    }

    public void changeValue(int value)
    {
        MyProperty = value;
    }
}

假设你有

interface ITest2
{
     int MyProperty_Get();
}

用这个class

可以实现这个接口也就不足为奇了
class Test2 : ITest2
{
    private int myProperty;
    public int MyProperty_Get()
    {
         return myProperty;
    }

    //Not in the interface..
    public void MyProperty_Set(int value)  
    {
         myProperty = value;
    }
}

您可以将 set 函数添加到 class 实现中,即使接口中没有定义 set 函数。编译器不反对。这正是您在原始示例中所做的。

接口所做的只是声明任何实现 class 将做的 最低限度 。这是一个合同 "every type that implements this interface will have these properties and methods." 它 没有 将实施 class 限制为 定义的方法和属性在界面上。

例如,如果您有一个实现了 IDisposable 的 class,您认为 class 除了 Dispose() 方法之外没有其他功能吗?

当您将对象用作接口而不是具体类型时,接口定义了您可以对对象执行的操作:

public int CountItems(IEnumerable<int> items)
{
    return items.Count();
}

以上是一个非常简单的例子,但足以说明这一点。可以通过以下两个调用调用该方法:

CountItems(new [] {1, 2, 3});
CountItems(new List<int> {1, 2, 3});

内部方法只关心发送给它的对象是否公开在 IEnumerable<T>.

上找到的 Linq 方法 Count()

因此对于您的示例界面,您所说的只是 "if you operate on this interface, all you're ever going to be able to do is to get the value of MyProperty."

因此,所有这些 class 都是有效的:

public void Test1 : ITest
{
    public int MyProperty { get; private set; }

    public void changeValue() 
    {
        this.MyProperty = 12;
    }
}

public void Test2 : ITest
{
    public int MyProperty { get; set; }

    public void changeValue()
    {
        this.MyProperty = 9;
    }
}

如果您尝试执行的操作需要在没有方法的情况下设置该值,那么您将不得不将该操作限制为仅适用于 Test2,或者重新设计界面.但是,如果您不需要使用 setter,那么界面上缺少一个就可以满足该定义。