撰写伟大的Javadoc的技术提示

你有什么技巧来写伟大的Javadoc?

我正在寻找超越标准的“解释function”的内容提示。 我们都知道! (对?)

我对这样的事情感兴趣:

  • 什么标签应该是Javadoc的一部分,哪些不值得记住?
  • 你什么时候使用@see{@link}
  • 总是有必要使用@ @param显而易见的参数?
  • 你如何防止重写@param@return文本的方法的描述?
  • 在Javadoc中包含HTML是否合适?

最后,任何人都可以指出一个好的,简洁的Javadoc标签列表?

  • 我会说最重要的是@author @deprecated@return @inheritDoc@return @inheritDoc@return @param@return @inheritDoc@return @inheritDoc 。 但是你应该看看所有的标签,以防万一。
  • 在文本中使用@link作为解释,而@see作为引用列表。
  • “是否有必要使用@ @param显而易见的参数?” 没有。
  • {@inheritDoc}使用{@inheritDoc}
  • 这是一个标签列表 。

我一直在对JavaDocs的可用性进行博士研究,而且我的发现实际上违背了Sun提供的“正式指导方针”(文档一切和文档都很好),并提供了对“敏捷”方法的支持(写出有用的东西)。

简而言之,问题在于:当你编写所有的东西的时候,你基本上是在编写一个规范 – 详细的细节让那些“真正关心”的人学习关于你的函数的一切,并且可能编写一个完整的testing计划。 这在许多应用中很重要。

但是,在日常的开发情景中,没有一个开发人员真的会花时间阅读你提供的所有东西(我可以向你展示数字)。 他们会撇去,他们会错过信息。

通常来说,沟通最重要的事情是指令 – 通常不会做指示,或警告和其他“令人惊讶”的信息。 只有一些方法传达这些,而且在规范中经常丢失。

通过编写精心devise的JavaDocs,您实际上隐藏了重要的指令并减less了它们被使用的机会。 用户也往往避免阅读看起来太长的JavaDocs。

我对这个问题的解决方法是显式标记指令,所以用户浏览JavaDocs就会看到它们。 我在我的网站上有一个标签列表。

我还开发了一个名为eMoose的工具 ,突出了有指令的调用,我们已经获得了良好的实验结果,今年我们将在EclipseCon上展示它。 联系我,如果你想更多的数字,我有。

至于你特别提到的问题:如果你把所有的东西都logging下来,那就根据Sun的规格来做,但这意味着logging甚至是明显的东西。 尽量避免添加HTML,因为它会损害可读性而不使用IDE。 “干净的代码”这本书有很多文档。

以下是我们通过调查许多API所发现的自定义标签:

  • usage.restriction – 禁止从某些上下文中使用该方法(例如,“不要从UI线程调用”)或定义允许进行调用的实体(例如,“仅从debugging基础结构调用”)

  • usage.protocol – 传递一些调用序列。 例如“在调用X之前不要调用它”或者“在调用这个之后记得通知Y”。

  • usage.threading – 传递与线程相关的一些问题,例如需要使用系统线程或指示执行可能被阻塞。

  • usage.locking – 传达特定的locking要求

  • usage.performance – 传达给客户使用这种方法有一些性能问题。 例如,这需要很多时间

  • usage.parameter – 传递有关返回值的具体说明,如释放职责。 不要使用这个琐碎的东西(使用@param标签)。

  • usage.return – 传递有关返回值的具体说明,例如取消分配职责。 不要使用这个琐碎的东西(使用@return标签)。

  • usage.sideeffect – 警告用户一些与调用此方法相关的副作用

  • usage.security – 提醒用户注意与调用此方法相关的一些安全隐含或需求。

  • usage.alternative – 传达给用户他们可能想要使用不同的方法。 例如,“导致刷新,而不是调用X”。

  • usage.recommendation – 向用户传达他们可能想要执行的其他操作。 例如,“你可能想先validationurl”。

  • usage.limitation – 警告用户对方法工作方式的一些(意外的)限制。 例如,“不公布对听众的更改”

  • usage.patternrole – 向用户传达方法或类是模式的一部分。 几乎没有使用过。

  • usage.association – 向用户传达该方法或类与某个其他实体相关联。 几乎没有使用过。

在下面,我正在粘贴工具看起来像在使用的照片:在方法的JavaDoc中有两个标记的东西,其中一个调用突出显示,以表明它的目标有一个指令。

替代文字http://emoose.cs.cmu.eduhttp://img.dovov.comtagging_example.png

[编辑:添加(下面)从项目网站更新完整的eMoose Javadoc指令列表的纯文本版本。]

 /* @usage.general ...... No specific details @usage.restriction .. Forbids the use of the method from certain contexts (eg, "don't invoke from the UI thread") or defines the entities allowed to make the invocation (eg, "To be called only from debug infrastructure") @usage.protocol ..... Conveys some invocation sequence. For example "don't invoke this before you invoked X" or "remember to notify Y after calling this". @usage.threading .... Conveys some issues relating to threading, such as requiring the use of a system thread or indicating that execution may block. @usage.locking ...... Conveys specific locking requirements @usage.performance .. Conveys to the client that there is some performance issue with using this method. For example, that it takes a lot of time @usage.parameter .... Conveys specific instructions about the return value, such as deallocation responsibilities. Don't use this for trivial things (use the @param tag for those). @usage.return ....... Conveys specific instructions about the return value, such as deallocation responsibilities. Don't use this for trivial things (use the @return tag for those). @usage.sideeffect ... Alerts the user to some sideeffect associated with invoking this method @usage.security ..... Alerts the user to some security implications or requirements associated with invoking this method. @usage.alternative .. Conveys to the users that they may want to use a different method. For example, "to cause a refresh, call X instead". @usage.recommendation Conveys to the users that they may want to perform additional operations. For example, "you may want to validate the URL first". @usage.limitation ... Alerts the user to some (unexpected) limitation in how the method works. For example, "does not announce changes to listeners" @usage.patternrole .. Conveys to the user that the method or class is part of a pattern. Rarely used. @usage.association .. Conveys to the user that the method or class is associated with some other entity. Rarely used. @todo.task .......... Indicates a remaining action item that would constitute an entire task (relevant primarily to full version) @todo.step .......... Indicates a remaining item that would constitute a mere step in an entire task (relevant primarily to full version) @todo.local ......... Indicates a small action item relevant to the current location. Essentially equivalent to a //todo comment @todo.lookout ....... Indicates a need to be watchful for something in the future (relevant primarily to full version) @todo.refactor ...... Indicates a need to refactor the material at the current location @todo.optimize ...... Indicates a need to optimize the material at the current location. @bug.general ........ General bug @bug.task ........... Indicates a bug in the current task (relevant primarily to full version) @bug.unrelated ...... Bug unrelated to current task (relevant primarily to full version) @bug.resolved ....... Indicates that a bug has been resolved in this location @bug.filed .......... Indicates that a certain bug (with given information) has been filed at this location */ 

除了你的具体问题之外,我还是build议你一定要记住,当你写你的javadoc你的目标受众(API用户),以及你在那里放置什么样的细节。

您必须指定行为而不是实施细节。

对于一个很好的解释,为什么谁比谁在这个问题上的专家,约书亚布洛赫

这里是谈论如何devise一个良好的API和为什么重要

这有点冗长但值得。

考虑到这一点,你可以写一个有用的@return标签,不泄漏实现细节。

同行评审。

尝试在你的团队(客户)之外find一个人,并询问他们对JavaDoc的看法。

顾客永远是对的。

关于编写javadoc的一个很好的阅读是在http://www.oracle.com/technetwork/java/javase/documentation/index-137868.html

我从这个文本中学到的最好的东西可能是你的类级别的javadoc应该以“提供”开始。 这迫使你想想这个课程给你的程序(或世界)提供了什么。 我重新devise软件并不罕见,因为编写javadoc让我觉得“嘿,这里不需要这个!”。

其他实用技巧:当一个getter很有趣的时候,试着把它写在@returns标签中。 不这样做可能意味着你input东西两次,一次在javadoc中,一次在@return标签。

最好的提示:如果你不知道该写什么,不要这样做。 例如,Javadocparsing器在自动生成getter javadoc方面做了很多工作,但是只有当您没有添加/ ** * /时才会这样做。

Javadoc应该描述你的方法做什么,而不是如何。

Javadoc不是你的todolist。 我已经尝试过,但对于大型项目,它根本不起作用。

我认为,除非你build立一个图书馆以供广泛使用,否则就不需要像@param这样的东西(这通常从上下文和命名中清楚)。 实际上,我发现他们更麻烦,而不是因为他们是我可能忘记在重构阶段修复的东西。

对我更有用的是这样的事情:

函数在边缘情况下如何performance? 如果你给它一个null,它会做什么? 它会永远返回一个null?

– 在什么情况下抛出它是列出的例外

– 关于input对象的状态有什么假设?

再一次,这可能是因为这些是我需要回头去查的东西,而且我写的大部分javadoc都是为我自己或者小团队的同事而做的。 目标受众越大,我觉得我需要的越严格。

另一个重要的提示是,如果您正在编写抽象类或接口,请确保从视觉上分离将使用此层次结构中对象的方法的受众文本以及将覆盖该方法的受众。

太多的框架javadocs向客户提供forms为“子类应该知道X的forms”的块。 让子类很容易看到这些,而对于那些不是子类的人来说,要避免它们。 千万不要混合没有足够的垂直距离。

我曾经在这个问题上做了一些研究,我发现Javadoc最好的做法是随意的,杂乱无章的。 特别是我发现了这六个来自Sun的链接( 1 2 3 4 5 6 )。 在我看来,这种材料可以更好地组织和凝聚在某种程度上。

此外,作为一边,由javadoc生成的HTML是严重过时的。 它甚至不是有效的HTML。 我意识到在那里有javadoc doclet ,但是看到Sun的官方支持会很高兴。 JavaFX有一些有前途的文档技术,但据我所知,不能用于Java代码。