2013-02-27 223 views
0

最近我已经注意到为特定实体分配一个id的约定,引起我注意的是如果id不在那里,则返回-1。为什么返回-1而不是0?为什么返回-1而不是0?

protected long AcqAgreementID 
{    
    get 
    { 
     if(ViewState["AcqAgreementID"] != null) 
     { 
      return Convert.ToInt64(ViewState["AcqAgreementID"]); 
     } 
     else 
     { 
      return -1; 
     } 
    } 
} 

+4

在某些情况下,0是一个有效值 – CodesInChaos 2013-02-27 13:21:36

+0

我的问题看起来很蠢,我得到减号。 – 2013-02-27 13:26:45

+0

如果通过返回-1或0你想显示发生错误,你应该继续使用-1。返回0代替或任何其他值作为错误代码的意思,你的退出没有任何错误退出。这只是一个古老的最佳做法。 – 2013-02-27 13:30:52

回答

1

通常0是一个有效的id或返回值。想想一个具有索引或搜索字符串的控件。当为包含多个项目的控件查找选定索引或查找字符串中某个字符的索引时,返回值0是完全正常的。索引0表示选择的第一个项目或在字符串中的第一个位置找到一个字符。在这两种情况下,当没有选择或找到任何内容时返回-1。

+1

我非常喜欢你的答案。简单而亲切。谢谢兄弟。 – 2013-02-27 15:01:22

6

我期望-1被选择,因为值不能被用于一个ID。在这种情况下,它可以用来表示ID是无效的。

这个函数的设计者似乎希望调用者检查返回值是否是特殊的sentinel值-1。如果返回-1,则调用者需要采取适当的步骤。例如,调用者可能会显示或记录错误消息。

+0

这同样适用于具有多种数据库方案的'0' – CodesInChaos 2013-02-27 13:24:01

+0

@David Heffernan:那为什么不是0? – 2013-02-27 13:24:25

+1

@HumayounKabir只有代码的作者才能回答这个问题。也许0是一个有效的ID。也许不是。即使0无效,-1更明显是一个不好的值。此外,-1的值经常用于指示无效的数组索引,因此该用例的熟悉程度可能会渗透到这个用例中。 – 2013-02-27 13:25:49

0

在大多数情况下,您都不应该返回。很可能你应该抛出异常。

返回0或-1意味着调用程序必须检查这个已知的错误值,而不是简单地捕获异常。

+0

我不同意。我看到两种情况1)如果应用程序期望非零值,则引发异常就没有问题。但在这种情况下不应该被捕。 2)调用代码需要处理缺少的值。在这种情况下,它应该检查它是否有效。 (也许使用'TryGetAgreementID'方法)。不要对控制流使用异常处理。 – CodesInChaos 2013-02-27 13:27:03

+0

从给出的代码示例看,这看起来像是一个应用程序异常。 – 2013-02-27 14:23:01

+0

我同意例外不应该用于流量控制 从给出的代码示例看,这看起来像是应用程序异常。 抛出异常允许您提供更多的上下文和帮助。而不是返回0或-1,抛出一个自定义异常允许你明确说明发生了什么。您可以抛出一个AcqAgreementIDNotSetExcption来指示ViewState值为null或AcqAgreementIDWrongFormatException指示从ViewState检索的值格式错误。 也会记录和跟踪异常情况。 – 2013-02-27 14:29:22

0

这是一个简单的情况magic numbers反模式。

不应该这样做。应使用Consts或定义(取决于语言)。

幻数一般;导致WTF和像你一样的问题。

+0

如果在无效呼叫的情况下会添加抛出异常的可能性,我会加倍努力。 – 2013-02-27 13:23:47

0

这个问题是有点开放式的,不知何故太笼统;用“取决于”这样的东西来回答真的很容易。 一般来说,当0是一个完全合法的域值时(例如,它在ID的允许范围内),您使用负值:

然而,这不是一个好的模式:它会留下函数的用户/ API困惑(像你)。你必须弄清楚函数返回一个域中的数字(正整数),并且负值是不可能的,因此用作“invalud”值。

在C#/ .NET中,例如您应该考虑可空类型。他们通过添加额外的“值/状态”(null)来明确地说“这个值不在域中”。 除了可空类型,你应该考虑其他有效的约定是:

  • 抛出一个异常(像Int.Parse)
  • 添加out参数来表示有效性或没有(像Int.TryParse)
+1

可能会让自己陷入混乱。我同意你的“取决于”...但是,然后反驳为“应该使用可为空”......这又是一个“取决于”。 – 2013-02-27 13:29:39

+0

@MatthewWhited权利,我编辑它“应该考虑”。可空类型和关系数据库中的NULL之前(为此目的而发明的)(对于出现错误/非初始化条件的情况,具有非域值) – 2013-02-27 13:32:01

+1

@ dema80:此id字段不能是可空的整数它是该实体的主要关键领域。 – 2013-02-27 13:32:10

0

我已经使用这种模式在我想为一个ID使用一个不可为空的整数值的地方。我不喜欢使用0作为“default”/“unassigned”ID,因为它是整数类型的默认值。这允许我查看模型对象,以确定它们是否应该插入或更新,并且我也可以告诉它是否未知“0”。

这取决于你的体系结构,从其他几个帖子中可以看出,它可以通过可为空的非可空ID来构建宗教战争。

...

作为一个说明我还看到/使用的模式,其中模型有其用已知的值,如-1 colleased(??)呼叫前进入功能可空类型/数据模型需要非空类型。我们总是参与开发项目,这是“它取决于”的真棒世界。

1

这是在.NET框架中返回索引的方法的标准。

public int FindIndex( Predicate<T> match)方法返回匹配 通过匹配所定义的条件下,如果发现了一个元件的第一次出现的 从零开始的索引;否则,-1。

http://msdn.microsoft.com/en-us/library/x1xzf2ca.aspx

这使主叫方可以办理ID /索引不被发现,他们想要的任何方式。他们可能会抛出异常或从其他来源获取ID;他们想要什么。

可空类型本来可以使用,但是这些方法的标准是在引入可空类型之前开发的。如果你可以控制这段代码,你可以考虑改变它,但是返回-1没有问题。肯定不会返回0,因为0通常是一个有效的ID /索引。

相关问题