记录科学软件的好方法是什么?

计算科学 软件 文件
2021-12-02 19:40:27

很多时候,当我继承或遇到其他人(或偶尔,甚至是我自己的工作)编写的科学代码时,我注意到文档要么稀疏要么不存在。如果幸运的话,我会看到内容丰富的评论。如果我很幸运,甚至还有 Doxygen 注释和一个 Doxyfile,这样我就有了函数接口和一些格式化的 HTML 可供查阅。如果我非常幸运,除了 Doxygen 和源文件注释之外,还有 PDF 手册和示例,我欣喜若狂,因为它让我的生活变得更加轻松。

哪些信息和工具对记录源代码有用?就此而言,在科学软件的情况下,哪些信息和工具可用于记录伴随该源代码的数据和结果?

4个回答

我认为科学软件的文档可以分为三类,所有这些都是充分理解所必需的。最简单和最常见的是单独的方法文档。为此有很多系统。你提到了doxygen,Python 有pydoc,在 PETSc 中我们有自己的包播种,它会生成以下内容

但是,对于任何超出简单实用程序的软件,您都需要一本手册。这提供了包用途的高级视图,以及它的不同功能如何集成以实现此目的。它通常通过使用示例来帮助新用户构建他们的代码。在 PETSc 中,我们只是使用 LaTeX 作为手册,但PyClaw包使用了Sphinx框架,我对此印象非常深刻。我们在播种包中实现的一件我觉得非常有用的事情是示例代码和函数文档之间的链接。例如,这个例子求解 Bratu 方程。请注意,您如何可以按照任何自定义类型或函数调用的链接访问低级文档,以及这些页面如何链接回使用它们的示例。这就是我了解项目中其他人贡献的新功能的方式。

我认为,文档中经常被忽视的部分是开发人员文档。发布编码风格的文档以及与存储库交互的说明并不少见。然而,在实施之前解释设计决策是非常罕见的。这些决策总是涉及权衡,硬件和算法的情况必然会随着时间而改变。如果没有讨论权衡审查和特定设计决策的基本原理,以后的程序员只能自己重新创建整个过程。我认为当原始开发人员不再负责时,这是成功维护和改进旧代码的主要障碍。

代码内文档

最重要的是在您选择的开发环境中使用文档工具,这意味着python 的pydoc、java中的javadoc或 C# 中的xml 注释这些使得在编写代码的同时编写文档变得容易。

如果您依赖于稍后回来并记录事情,您可能无法解决它,但如果您在编写代码时这样做,那么需要记录的内容将在您的脑海中浮现。如果 XML 文档不完整或与实际代码不一致,C# 甚至可以选择发出编译警告。

测试作为文档

另一个重要方面是具有良好的集成和单元测试。

通常,文档集中于类和方法孤立地做什么,而忽略了它们是如何一起使用来解决您的问题的。测试通常通过显示它们如何相互交互来将它们置于上下文中。

类似地,单元测试通常会明确指出外部依赖关系,通过这些依赖关系需要Mock出来。

我还发现使用测试驱动开发我编写的软件更易于使用,因为我从一开始就使用它。有了一个好的测试框架,让代码更易于测试和易于使用通常是一回事。

更高级别的文档

最后是关于系统级和架构文档的事情。许多人会提倡在 wiki 中或使用 Word 或其他文字处理器编写此类文档,但对我而言,此类文档的最佳位置是代码旁边,采用版本控制系统友好的纯文本格式。

就像代码内文档一样,如果您将更高级别的文档存储在代码存储库中,那么您更有可能使其保持最新。您还可以获得这样的好处,即当您提取代码的 XY 版本时,您还可以获得文档的 XY 版本。此外,如果您使用 VCS 友好的格式,那么这意味着很容易分支、区分和合并您的文档,就像您的代码一样。

我非常喜欢reStructuredText (rst) ,因为它很容易使用sphinx从中生成 html 页面和 pdf 文档,并且比LaTeX更友好,但仍然可以在需要时包含LaTeX 数学表达式。

我会反对法希姆提出的几乎每一点。具体来说:

1/“我认为期望科学开发人员花费大量时间记录他们的软件是不现实的”。这是一个失败项目的处方,很快没有人可以使用没有访问主要开发人员的权限。大型科学计算库(例如 PETSc 或 deal.II)拥有超过 1,000 页或更多页的大量文档是有充分理由的。如果没有大量文档,就不可能拥有庞大的用户社区。但是,我同意示例代码需要简单并专注于单个概念。

2/“如果合适,作者应考虑撰写论文发表”。这在实践中通常是不可能的。人们可以写关于概念和算法的论文,但不能写关于界面和其他设计决策的论文。此类论文的读者将了解该实现的作用;实现的用户将需要知道要调用哪些函数、参数的含义等。作为用户,大多数时候可以没有前者,只需将库视为黑匣子,但不能没有接口信息。

这是一个很好的问题。大致上,代码应该尝试自我记录。因此,例如,如果软件是命令行,您应该能够执行executable --helpexecutable -h什至executable(如果可执行文件不执行任何操作且没有参数),并返回简短的使用消息。

其次,我认为期望科学开发人员花费大量时间记录他们的软件是不现实的,所以我建议保持简单。包含基本方法和选项以及带注释的工作和测试的简短文本手册使用示例,从简单到更复杂(使用示例非常重要且经常被忽视)比没有好得多,而且比大多数科学软件提供的要多得多。我还想补充一点关于使用示例的烦恼。简单意味着简单。这意味着如果你试图说明一种方法,你不要添加十个无关的概念或方法来混淆读者。保持简单并进行注释,以便读者知道示例应该做什么。我还建议以某种方式将手动使用示例绑定到测试套件中,以便它们在代码更改时继续工作。我实际上不知道如何以一种好的方式做到这一点,所以请随时教育我。如果开发人员想要更花哨,确保他们可以使用漂亮的标记语言等等,添加手册页等等。

第三,如果合适,作者应该考虑写一篇论文发表。这通常会解决设计决策,并提供比手册更高级的软件视角,或者可以预期这样做。这将解决@Matt 正在谈论的设计决策的文档。

当然,最重要的文档是代码本身,应该根据需要对其进行注释。这假设代码是免费软件。如果不是,那么它作为科学软件的用处就会大大降低(你真的想使用一个你看不到方法是如何实现的黑盒子吗?)而且我不会使用它。