返回此值而不是void是否有任何缺点?

时间:2020-03-05 18:51:40  来源:igfitidea点击:

说一个方法而不是返回void,而是返回对该类的引用,即使该类没有任何特殊的语义意义。在我看来,它为我们提供了有关如何调用方法的更多选择,使我们可以以流畅的界面风格使用它,并且我真的没有想到任何缺点,因为我们无需执行任何操作与返回值(甚至存储它)。

因此,假设我们处于要更新对象然后返回其当前值的情况。
而不是说

myObj.Update();
var val = myObj.GetCurrentValue();

我们将可以将这两行结合起来说

var val = myObj.Update().GetCurrentValue();

编辑:我回想起下面的问题,回想起来,我同意它可能是不必要的和复杂的,但是我关于返回此问题而不是无效的问题。

在相关说明中,你们对使用该语言的看法包括新的语法糖:

var val = myObj.Update()<.GetCurrentValue();

此运算符的优先级较低,因此将先执行myObj.Update(),然后在myObj上调用GetCurrentValue(),而不是无效的Update返回。

本质上,我在想象一个运算符,该运算符将说"在运算符右侧的左侧第一个有效对象上调用方法"。有什么想法吗?

解决方案

回答

返回"自身"或者"此"是一种常见模式,有时也称为"方法链接"。至于我们建议的语法糖,我不太确定。我不是.NET专家,但是对我来说似乎并不是很有用。

回答

NeXTSTEP Objective-C框架用于使用此模式。一旦将分布式对象(基本上是远程过程调用)添加到语言中,该框架就不再使用了,返回" self"的函数必须是同步调用,因为分布式对象系统看到了返回类型并假定调用者需要知道函数的结果。

回答

我认为,作为一般政策,这根本没有道理。以这种方式进行方法链接可使用正确定义的接口,但只有在具有语义意义的情况下才是合适的。

示例是一个不合适的主要示例,因为它没有语义上的意义。

同样,通过正确设计的流利界面,我们不需要语法糖。

流利的接口或者方法链接可以很好地工作,但是需要仔细设计。

回答

我知道在Java中,他们实际上是在考虑使void方法成为这种标准行为。如果这样做,则不需要多余的语法糖。

我能想到的唯一缺点是性能。但这很容易衡量。几分钟后,我会尽快与我们联系:-)

编辑:

返回引用要比返回void慢一些。所以这是唯一的缺点。调用函数时要多打几分。

回答

我可以看到的唯一缺点是,它使API变得更加混乱不清了。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。假设我们有一个带有remove()方法的集合对象,该对象通常会返回void。现在,我们想返回对集合本身的引用。新的签名如下所示:

public MyCollection remove(Object someElement)

仅查看签名,尚不清楚我们是否返回对同一实例的引用。也许MyCollection是不可变的,并且我们要返回一个新实例。在某些情况下,例如此处,我们将需要一些外部文档来阐明这一点。

我实际上很喜欢这个主意,并且我相信在Java7中改装所有void方法以返回对" this"的引用时,有一些讨论,但最终失败了。

回答

这不是像JQuery所利用的"流利接口"的构建方式吗?好处之一是应该具有代码可读性(尽管http://en.wikipedia.org/wiki/Fluent_interface上的Wikipedia条目提到有些人认为它不可读)。另一个好处是代码简洁,我们无需在7行代码中设置属性,然后在第8行对该对象调用方法。

马丁·福勒(Martin Fowler,在此处创造了该术语,网址为http://martinfowler.com/bliki/FluentInterface.html)说,流利的接口要比方法链更多,但是方法链是与流利的接口一起使用的一种常用技术。

编辑:
我实际上是回到这里来编辑我的答案,并补充说,当我看到George的评论指出我确实忘记讨论问题的要点时,以任何可衡量的方式返回它而不是无效没有任何不利之处。抱歉,最初的"毫无意义"的漫步。

回答

乍看起来可能看起来不错,但是对于一致的接口,我们将需要所有方法都返回对此的引用(这有其自身的问题)。

假设我们有一个带有两个方法GetA的类,该方法返回此对象,而GetB返回另一个对象:

然后,我们可以调用obj.GetA()。GetB(),但不能调用obj.GetB()。GetA(),至少看起来不一致。

使用Pascal(和Visual Basic),我们可以调用同一对象的多个方法。

with obj
  .GetA();
  .GetB();
end with;

此功能的问题在于,我们可以轻松编写比应理解的难理解的代码。另外,添加新的运算符可能会使操作变得更加困难。