c# - 自动属性的默认接口(interface)方法和默认值

标签 c# c#-8.0 default-interface-member

鉴于自动属性编译为 get_methodset_method 和私有(private)变量,并且由于 C# 8 正在引入默认接口(interface)方法

接口(interface)中的属性可以有默认实现吗?

尤其是只获取属性?

最佳答案

否和是。接口(interface)不能有状态,但您可以使用 {get;set;} 定义属性。

自动属性不是一种特殊类型的属性。它们是一种便利的功能,可以生成将属性值存储在支持字段中所需的代码。

您可以为属性指定默认实现,包括 getter 和 setter。您可以在Sharplab.io中尝试以下代码

public interface IDimensions
{
    int Height {get;set;}
    int Width {get;set;}
    int Depth {get;set;}

    int Weight { get=>0; set{} }
    int Density { get=> Weight==0?0:Height*Width*Depth/Weight ; }
}

public class Box:IDimensions
{
    public int Height{get;set;}
    public int Width{get;set;}
    public int Depth {get;set;}
}

版本控制

这演示了版本控制场景。 Box 实现了 IDimensions 的一个版本,它只包括 HeightWidth

Weight 是后来添加的,默认实现返回 0 并忽略写入。 Density 添加了一个默认实现,该实现返回一个盒子的体积/密度,如果没有有效重量则返回 0。 Box 不必改变,即使 interfade 改变了。甚至编译器生成的代码也没有显示对 Box 类的任何更改。

类可以用自己的实现替换默认实现。没有什么能阻止 Box 将来添加 int Weight {get;set;}

默认实现只能通过接口(interface)使用:

IDimensions box=new Box();
Console.WriteLine(box.Density);

特质

默认实现处理的另一个场景是特征。

假设我想将 IDensity 特征添加到任何类型的项目。在大多数情况下,我只需要一个项目的体积和重量来计算它的密度:

public interface IDensity
{
    int Density 
    { 
        get 
        {
            var weight=getWeight();
            if (weight==0) return 0;
            return getVolume()/weight;
        }
    }

    abstract int getWeight();
    abstract int getVolume();
}

此特征将返回一个简单的密度计算并强制它所应用的类型实现 int getWeight()int getHeight() 方法:

public class Crate:IDensity
{
    //Dummy numbers
    public int getWeight()=>55;
    public int getVolume()=>100;
}

public class C {
    public void M() {
        IDensity box=new Cake();
        Console.WriteLine(box.Density);
    }
}

另一个容器可以用自己的实现覆盖该实现。也许容器的形状很复杂:

public class WeddingCake:IDensity
{
    public int getWeight()=>5;
    public int getVolume()=>getWeight()/Density;
    public int Density=>2;
}

此示例的 Sharplab.io 链接 is here

关于c# - 自动属性的默认接口(interface)方法和默认值,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53700939/

相关文章:

c# - CSS 标题颜色从左上逐渐变为右下

c# - 在 C# 中使用 SSH.NET SFTP 下载目录

c# - 如何调用默认方法而不是具体实现

c# - 可空引用类型和 ToString() 重载

c# 指示泛型成员的可空性

resharper - 为什么C#8接口(interface)成员的默认实现会报错

c# - 你将如何在 C# 中实现 "trait"设计模式?

c# - 如何在 MassTransit 和 Automatonymous 中配置 EF Core 持久性?

c# - 在 C# 中使用 StringBuilder 构造 HTML 的问题

C# 8 基本接口(interface)的默认方法调用解决方法