例如,假设我想要一个ICar接口,并且所有实现都将包含字段Year。这是否意味着每个实现都必须单独声明Year?在接口中简单地定义它不是更好吗?
当前回答
从c# 8.0开始,接口可以为成员定义默认实现,包括属性。很少在接口中为属性定义默认实现,因为接口可能不定义实例数据字段。
https://learn.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/interface-properties
interface IEmployee
{
string Name
{
get;
set;
}
int Counter
{
get;
}
}
public class Employee : IEmployee
{
public static int numberOfEmployees;
private string _name;
public string Name // read-write instance property
{
get => _name;
set => _name = value;
}
private int _counter;
public int Counter // read-only instance property
{
get => _counter;
}
// constructor
public Employee() => _counter = ++numberOfEmployees;
}
其他回答
已经说了很多,但为了简单起见,这里是我的看法。 接口的目的是拥有由使用者或类实现的方法契约,而不是使用字段来存储值。
你可能会问为什么允许有财产?因此,简单的答案是—属性在内部只定义为方法。
简短的回答是肯定的,每个实现类型都必须创建自己的支持变量。这是因为接口类似于契约。它所能做的就是指定实现类型必须提供的特定的公开可访问的代码段;它本身不能包含任何代码。
用你的建议来考虑这个场景:
public interface InterfaceOne
{
int myBackingVariable;
int MyProperty { get { return myBackingVariable; } }
}
public interface InterfaceTwo
{
int myBackingVariable;
int MyProperty { get { return myBackingVariable; } }
}
public class MyClass : InterfaceOne, InterfaceTwo { }
这里有几个问题:
因为接口的所有成员(根据定义)都是公共的,所以我们的备份变量现在暴露给使用该接口的任何人 MyClass将使用哪个myBackingVariable ?
最常用的方法是声明接口和实现它的基本抽象类。这使得您可以灵活地从抽象类继承并免费获得实现,或者显式地实现接口并允许从另一个类继承。它是这样工作的:
public interface IMyInterface
{
int MyProperty { get; set; }
}
public abstract class MyInterfaceBase : IMyInterface
{
int myProperty;
public int MyProperty
{
get { return myProperty; }
set { myProperty = value; }
}
}
c#中的接口旨在定义类将遵循的契约——而不是特定的实现。
基于这种精神,c#接口确实允许定义属性——调用者必须为其提供一个实现:
interface ICar
{
int Year { get; set; }
}
实现类可以使用auto-properties来简化实现,如果没有与属性相关的特殊逻辑的话:
class Automobile : ICar
{
public int Year { get; set; } // automatically implemented
}
其他人已经给出了“为什么”,所以我只是补充说,你的界面可以定义一个控件;如果你把它包装在属性中:
public interface IView {
Control Year { get; }
}
public Form : IView {
public Control Year { get { return uxYear; } } //numeric text box or whatever
}
为此,您可以有一个实现year字段的Car基类,所有其他实现都可以从它继承。
推荐文章
- 实体框架核心:在上一个操作完成之前,在此上下文中开始的第二个操作
- 如何为构造函数定制Visual Studio的私有字段生成快捷方式?
- 如何使用JSON确保字符串是有效的JSON。网
- AppSettings从.config文件中获取值
- 通过HttpClient向REST API发布一个空体
- 如何检查IEnumerable是否为空或空?
- 自动化invokerrequired代码模式
- 在c#代码中设置WPF文本框的背景颜色
- 在c#中,什么是单子?
- c#和Java中的泛型有什么不同?和模板在c++ ?
- c#线程安全快速(est)计数器
- 如何将此foreach代码转换为Parallel.ForEach?
- 如何分裂()一个分隔字符串到一个列表<字符串>
- 如何转换列表<字符串>列表<int>?
- c#对象列表,我如何得到一个属性的和