2012-06-22 70 views
7

我有一个包含项目集合的类。为方便起见,我提供GetCurrentItem这是由创建可能抛出的属性IndexOutOfRangeException

public Type GetCurrentItem 
{ 
    get { return this.items[this.items.Count - 1]; } 
} 

如果在列表中没有的项目,这将抛出一个异常实现。

我应该抛出异常还是应该返回null?如果这是我交给你的API,你会期望什么?异常或null?有没有更好的方法来处理这个问题?

+2

这是正确的API:'Enumerable.Single'或'Enumerable.SingleOrDefault'? (回答:它取决于) –

回答

9

至于哪一个更正确?正如柯克的评论所暗示的那样:这取决于。有时候null是合乎逻辑的,如果没有默认值是合理的,有时例外更适合。我试图做的一件事就是想到“是否呼叫GetCurrentItem逻辑失败或安全的事情?”

如果在没有任何东西的情况下调用GetCurrentItem失败,则抛出异常是正确的过程。例如,如果您的收藏有HasCurrentIsEmpty属性,在致电GetCurrentItem之前某人可以检查结果,那么他们应该“知道得更清楚”。但是如果当前的项目是null是使用你的课程的正确逻辑方式,那么通过一切手段来设计它。无论哪种方式,我都会在代码注释中记录行为,让用户知道预期的行为。

虽然我会这样说,但暴露了ArgumentOutOfRange异常可能是出血执行的细节。也就是说,如果这个类的用户不知道内部结构是一个数组还是List<T>,那么不要流出这个异常,而是抓住它,包装它,然后抛出一个更有意义的(自定义或类似的东西InvalidOperationException)。

因为他们没有真正直接传递一个说法,他们得到一个ArgumentOutOfRange的例外可能是混乱:-)

+0

异常的一个好选择是'InvalidOperationException',遵循'Stack .Peek()'设置的示例。 –

+0

@MichaelLiu:是的,同意。我在编辑时加入了,就像你评论过的那样:-) –

3

让它抛出一个错误。这就是其他收藏的工作原理。应该由用户应用程序来处理潜在的异常(特别是在处理集合时)。在继续之前,用户可以调用bool HasSelection()方法。

3

例外情况应该用于例外情况。如果CurrentItem可以为null,则不应抛出异常。我不明白为什么没有一个CurrentItem是例外。

1

然后,问题是你是否希望GetCurrentItem返回一个安全值。如果Type是可空的,那么当没有当前项目时,GetCurrentItem可能应该返回null。如果你总是期望列表是非空的,并且总是有默认选择的东西,那么抛出一个有意义的异常。

你通常不应该抛出一个异常,除非你的情况确实是一个异常,而不是一个正常的用例。但是,这可能是相当主观的。

0

如果GetCurrentItem让你的API的意义时,有没有项目我会抛出“InvalidOperationException异常”。如果允许null作为有效结果,您可能想要以不同的方式命名它。

考虑现有的LINQ Last方法是否已经提供了相同的功能。

1

我试图从用户的角度思考它。去Principal of Least Astonishment

如果我用的是库或对象,并呼吁GetCurrentItemIndexOutOfRangeException被抛出,我会想,“我没有与索引叫什么,我想当前的项目。”因此,我的建议是返回null,这会让我想,“哦,没有当前项目。”

或者,如果这个属性是一个索引器,我想要得到一个特定索引的项目,我不会感到惊讶的是一个IndexOutOfRangeException

相关问题