10

我很想添加一个像“Ex”这样的后缀来区分抛出异常的方法(具有相似的签名)和不抛出异常的方法。

有这样的约定吗?

4

11 回答 11

21

是的,您将它们命名为与未命名的方法相同。

异常规范还不够吗?

编辑:如果您有类似的抛出/不抛出方法,我推荐Parse/TryParse模式(Parse被操作替换)。.NET Framework 经常使用它(Dictionary<T,K>.TryGetValueMonitor.TryEnterint.TryParse等)。

编辑:编码恐怖:TryParse 和例外税

于 2009-07-23T01:46:08.193 回答
16

不要那样做。

这就像问“是否有将两个字符串作为参数的方法的命名约定”。

Java 已检查异常,这意味着您无论如何都需要声明它们。所以你可以很容易地看到是否会抛出异常,以及什么类型的异常。如果不添加异常处理代码,您甚至无法编译调用该方法的代码。

更新:似乎您的意图是拥有检查某个条件是否为真的方法,但您不想只返回假,而是在不满足条件时抛出异常,这样您也可以传达解释消息(在例外中)。我认为“断言”或“确保”的前缀是有道理的:

 // instead of
 if (! isAuthenticated())
    throw new NotAuthenticatedException("not sure why at this point...");

 // you do
 assertAuthentication();
 // which will throw NotAuthenticatedException("proper explanation") inside
于 2009-07-23T01:47:15.493 回答
8

为什么要在 Java 中做这样的事情?它已经在语言中内置了异常说明符。编译器会阻止您调用显式抛出异常的方法,而您没有采取一些措施来处理或允许传播异常?

于 2009-07-23T01:46:15.260 回答
3

如果您需要区分这些方法,我相信您可以在不使用后缀或任何东西的情况下在命名中做到这一点,这(正如其他人指出的那样)非常可怕。

为什么有:

boolean authenticate(String username, String password);

和(说)

void authenticateEx(String username, String password) throws WhateverException;

当您可以通过传达实际意图使其成为名称中有意义的部分时:

void ensureCanAuthenticate(String username, String password);

// or

void assertValidCredentials(...);

// or

void authenticateOrDie(...);

...或任何数量的其他(可能更好的)名称,它们实际上传达了意图,而不是依赖于令人困惑的后缀。

于 2009-07-23T10:50:50.273 回答
2

异常是 Java 中方法签名的一部分,因此这样的命名约定是多余的。

于 2009-07-23T01:47:29.517 回答
2

抛出异常的方法的匈牙利符号?奎尔恐怖!

你的意思是检查或未经检查的异常?你到底为什么要这么做?

当您考虑它时,您必须将您的约定添加到每个方法中,因为总是存在潜在的错误或 NPE 或其他可能出错的事情。

当您检查异常时,“抛出”子句就足够了,并且在上帝的绿色地球上对于未经检查的异常没有好的目的。

不要这样做。请。

于 2009-07-23T01:54:27.310 回答
1

没有约定,添加 ex 会使名称更难阅读,并且对于普通的 Java 程序员来说很难看。

但有时我可以想象,将尝试添加到可能引发异常的方法中会使您的代码更容易理解。特别是如果它们未选中。

它不必像在许多 c/c++ 程序中发现的那样丑陋,在这些程序中,成员使用 _name 或 mName 或整数使用 iValue。但是在java中也有一些约定。如果一个方法将返回一个以 is... 为前缀的整数,那么 set、get 和 test 是最常用的示例。所有这些都记录在方法头中,通过返回类型注释等......但是在函数名称中添加一个单词可以更容易和更快地阅读和理解。

为什么不使用 try 给阅读你代码的程序员一个潜意识的暗示,这个方法很可能会抛出异常。像 tryCopyFile 而不是 tryWriteFile。

于 2009-07-23T02:14:36.113 回答
0

没有这样的约定,因为每个方法都可以抛出异常,无论您是否声明它们。在这个 IDE 工具提示的时代,它也有些多余(当然,除非您没有使用 IDE)。

不过,我很想知道您为什么想使用这样的命名约定。

于 2009-07-23T08:09:26.933 回答
0

每隔一段时间,您就会遇到这样一种情况,即使用类似getSafely()( 在实际值无效的情况下返回默认值,对于不太关心实际值的代码) vs 占位符)或其相反getOrBlowUp()(对于快速失败的代码,其中缺失值在技术上是可能的,但表明应该设置值的代码中存在错误)。

但这里的重点不是“方法 2 抛出异常,方法 1 没有”——因为如上所述,任何代码都可能抛出RuntimeException. 关键是这两种方法具有不同的错误处理语义,特定于不同的用例,就是方法名称试图捕捉的内容。

即使那样,如果您可以摆脱一种或另一种行为并调用方法,代码通常会更干净get()

这里一个有用的类比可能是系统匈牙利语和应用程序匈牙利语在匈牙利表示法中的区别。(另请参阅Joel on Software关于编码约定的这篇文章。)

  • Systems Hungarian 只是告诉您变量的类型,因此整数count变为iCount. 这是匈牙利符号的最常见形式,恕我直言,它(1)对于现代 IDE 毫无意义,(2)如果有人更改类型声明而不重命名变量,则可能具有欺骗性。
  • Apps Hungarian 会告诉您变量的用途,因此表示数据行的整数(或短的或序号 ID 对象,或其他什么,谁在乎?)index变成drIndexindex表示注释列变成acIndex。这更有用,而且不太可能引起麻烦。

调用您的方法getEx()是 Systems Hungarian。

于 2009-07-23T09:44:50.967 回答
0

没有我知道的。

在我看来,唯一有意义的事情是在单元测试用例中(例如,testFooExpectingException())。但这并不是你在说的。

于 2009-07-23T02:17:07.607 回答
0

通常不要将其添加到方法名称中。

改为添加投掷。

int parseInt(String s, int radix) throws NumberFormatException

但我个人喜欢吸气剂,例如

    getFieldsOrThrow(java.lang.String key)
    getFieldsOrDefault(java.lang.String key, Value defaultValue)

https://developers.google.com/protocol-buffers/docs/reference/java/com/google/protobuf/Struct

于 2021-02-19T10:31:49.443 回答