我需要公开类实例的“已映射? ”状态。结果通过基本检查确定。它不是简单地暴露字段的值。我不确定应该使用只读属性还是方法。
只读属性:
public bool IsMapped
{
get
{
return MappedField != null;
}
}
方法:
public bool IsMapped()
{
return MappedField != null;
}
MappedField
意味着什么呢?它是对变量的简单读取,还是潜在的昂贵操作或具有副作用(例如延迟加载)的操作?
Answers:
C#标准说
第8.7.4节
甲属性是提供访问对象或类的特性的部件。属性的示例包括字符串的长度,字体的大小,窗口的标题,客户的名称等。属性是字段的自然扩展。两者都是具有关联类型的命名成员,并且访问字段和属性的语法相同。但是,与字段不同,属性不表示存储位置。相反,属性具有访问器,这些访问器指定在读取或写入其值时要执行的语句。
而方法定义为
第8.7.3节
甲方法是一种部件,其实现可以由对象或类执行的计算或操作。方法具有形式参数的列表(可能为空),返回值(除非方法的return-type为void),并且为静态或非静态。
使用属性和方法来实现封装。属性封装数据,方法封装逻辑。因此,如果要公开数据,则应首选只读属性。在您的情况下,没有逻辑可以修改对象的内部状态。您想提供对对象特征的访问。
对象的实例是否是对象IsMapped
的特征。它包含一个检查,但这就是为什么您有属性可以访问它。可以使用逻辑定义属性,但不应公开逻辑。就像第一个引号中提到的示例一样:想象一下该String.Length
属性。根据实现的不同,此属性可能会遍历字符串并计算字符。它也确实执行操作,但是“从外部”仅给出对象的内部状态/特性的声明。
我个人认为amethod
应该做某事或执行某些操作。您没有在内部执行任何操作,IsMapped
因此应该是property
在这种情况下,我似乎很清楚应该将其作为财产。这是一个简单的检查,没有逻辑,没有副作用,没有性能影响。没有比检查更简单的了。
编辑:
请注意,如果出现了任何上述的,你会把它变成一个方法,该方法应该包括一个强有力的动词,不是助动词像是或有。一种方法可以执行某些操作。您可以将其命名为VerifyMapping或DefineMappingExistance或其他名称,只要它以动词开头即可。
MappedField != null
根据定义,这是一种逻辑陈述。
MappedField
是简单,快速且没有副作用的。我们不知道那是真的。
我认为您链接中的这一行就是答案
方法代表动作,属性代表数据。
这里没有任何动作,只有一条数据。所以这是一个财产。
null
检查
在可以访问这两种构造的情况/语言中,一般的划分如下:
更具体地说,属性将用于以读取和/或写入方式访问(出于消费目的)由暴露该属性的对象拥有的数据成员。属性比字段更好,因为数据不必一直以持久形式存在(它们使您对数据值的计算或检索变得“懒惰”),并且它们比为此目的的方法更好。您仍然可以在代码中使用它们,就像它们是公共字段一样。
但是,属性不应导致副作用(可能的,可以理解的例外情况是,设置变量以保留返回的值,从而避免了多次昂贵的值的重新计算);在所有其他条件相同的情况下,它们应该返回确定性结果(因此NextRandomNumber是属性的错误概念选择),并且计算不应导致会影响其他计算的任何状态数据发生更改(例如,获取PropertyA和按此顺序排列的PropertyB不应返回与先获取PropertyB然后再获取PropertyA相同的结果。
OTOH方法在概念上被理解为执行某些操作并返回结果。简而言之,它会执行某些操作,可能会超出计算返回值的范围。因此,当返回值的操作具有其他副作用时,将使用方法。返回值可能仍然是某些计算的结果,但是该方法可能已经不确定地计算了该值(GetNextRandomNumber()),或者返回的数据采用对象的唯一实例的形式,再次调用该方法会产生一个不同的实例,即使它可能具有相同的数据(GetCurrentStatus()),或者该方法可能更改状态数据,使得连续两次执行完全相同的操作也会产生不同的结果(EncryptDataBlock();
我会同意这里的人的说法,因为它正在获取数据,并且没有副作用,所以它应该是一种财产。
进一步说,如果某人“从外面看”它的意义,我也会接受setter(而不是getter)的一些副作用。
一种考虑方法是方法是动词,属性是形容词(同时,对象本身是名词,而静态对象是抽象名词)。
动词/形容词准则的唯一例外是,在获取(或设置)所讨论的信息时,使用方法而不是属性可能是很有意义的:在逻辑上,此类功能可能仍应是属性,但是人们习惯将性能视为对性能的影响不大,尽管没有真正的理由为什么总是如此,但强调一下这一点可能会很有用 GetIsMapped()
相对较重的性能。
在运行代码的级别上,调用属性和调用等效方法来获取或设置绝对没有区别。所有这些都是为了使使用该代码的人的生活更加轻松。