Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/design-patterns/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
.net 接口不应该有属性?_.net_Design Patterns_Oop - Fatal编程技术网

.net 接口不应该有属性?

.net 接口不应该有属性?,.net,design-patterns,oop,.net,Design Patterns,Oop,我的办公室同事今天告诉我,在接口中使用属性是一种糟糕的做法。他在一些MSDN文章中提到了这一点,但我找不到(我在谷歌上尝试了几次,可能是用了错误的关键词)。他还告诉我,只有方法应该在接口中。 现在,我知道这不是严格的规则,因为在.net中,显然可以在接口中创建属性签名并编译它 但这真的是一种糟糕的实践/设计/面向对象编程吗?为什么 指出正确的文献或网络资源也会有帮助 谢谢我从来没有遇到过任何人提出这种说法,我也看不出有什么好的理由。NET framework中充满了带有属性的接口。接口是类要实现

我的办公室同事今天告诉我,在接口中使用属性是一种糟糕的做法。他在一些MSDN文章中提到了这一点,但我找不到(我在谷歌上尝试了几次,可能是用了错误的关键词)。他还告诉我,只有方法应该在接口中。 现在,我知道这不是严格的规则,因为在.net中,显然可以在接口中创建属性签名并编译它

但这真的是一种糟糕的实践/设计/面向对象编程吗?为什么

指出正确的文献或网络资源也会有帮助


谢谢

我从来没有遇到过任何人提出这种说法,我也看不出有什么好的理由。NET framework中充满了带有属性的接口。

接口是类要实现的契约,我认为没有理由将属性排除在此类契约之外。此外,属性是.NET固有的


例如:
ICollection
既有
Count
又有
IsReadOnly

从未见过这样的东西,但不久前有人谈论过不在跨平台接口定义中使用属性,因为有许多平台不支持属性,但是几乎所有东西都支持方法。

我想不出任何文档来支持这个前提。此外,我可以在BCL中想出许多与此相反的例子。看看几乎所有的集合接口,您将看到属性

实际上,属性由两个函数组成:一个用于获取值,另一个用于设置值。尽管属性是C#的第一类“特性”,但这仍然是事实


为什么接口中不允许使用属性?

我认为没有理由不将属性作为接口的一部分。您还将如何实现对数据成员的访问?获取方法并设置方法而不是属性。那简直太难看了,所以在20世纪90年代。

我也会在这里加上我的声音——我从来没有遇到过这个建议。属性实际上是一对get/set方法


就像其他设计决策一样。如果它真的有意义;如果它适用于设计中的系统,如果它不会导致维护问题,如果它不会导致性能问题,那么您就没有理由不这样做。

有一个广为认可的术语“代码气味”。我建议引入“程序员气味”的概念——如果有人坚持某种规则,但无法解释原因——这是一种气味。您的同事应该能够解释为什么接口中的属性不好。若他不能——即使他所指的文章是对的,他也可能是错的


这篇文章可能是在讨论一些特定类型的接口,可能是与COM和互操作性或其他相关的。或者他可能只是弄错了。理解规则并能够解释它们是使用规则的重要组成部分。

我能看到的属性与方法的唯一缺点是,尽管有一个与get方法的接口、一个与set方法的接口以及一个将两者结合在一起的接口是没有问题的(一种允许最大程度地灵活处理协变和逆变的方案),属性不能很好地组合。我不知道为什么读写属性不能简单地看作是读属性和写属性,但事实并非如此。如果接口支持同名的只读属性和只读属性,则任何通过组合接口访问属性的尝试都会失败这是一个糟糕的设计,因为你污染了实现的变量空间,该空间用于存储状态,变量用作类契约的一部分。

我唯一能想到的,为什么属性对接口不好的方法是,当你为服务(如WCF、WebServices、Remoting)定义接口时托管在不同计算机或应用程序域上的


原因属性意味着它们很快(即获取和设置值)由于网络和序列化活动,这对于服务来说是不正确的。在服务接口中获取或设置值的explizit方法意味着可能需要一些时间来完成操作。

对于需要属性作为接口成员的场景来说是一个完美的例子。如果不执行ce实现者这样做?

我知道这是一个.Net问题;然而,这种想法可能来自Java背景。它让我想起了有效Java中的第22项:仅使用接口定义类型

本建议并不禁止接口中的所有属性。它专门针对仅包含属性的接口

当类实现接口时,该接口充当可用于引用该类实例的类型。因此,类实现接口应该说明客户端可以对该类实例执行哪些操作。为任何其他目的定义接口是不合适的

一种未通过此测试的接口是所谓的常量接口。此类接口不包含任何方法;它仅由静态最终字段组成

常量接口模式不能很好地使用接口。类在内部使用某些常量是一个实现细节。实现常量接口会导致此实现细节泄漏到类的导出API中…它表示一种承诺:如果在将来的版本中对类进行了修改,使其不受影响不再需要使用常量,它仍然必须实现接口以确保二进制兼容性。如果非最终类实现常量接口,则其所有子类的名称空间都将被接口中的常量污染

当然,Java本身(可能还有C#)