1

我重新表述这个问题,因为它要么太无趣,要么太难以理解。:)

最初的问题是因为我正在从 Java 转换到 Groovy,但是当转换到任何高级语言(Ruby、Python、Groovy)时,该示例同样适用。

Java 很容易调试,因为代码行和相当细粒度的行为之间存在清晰的关系,例如使用 for 循环操作数组:

for ( int i=0; i < array1.size(); i++ )
{
    if ( meetsSomeCriterion(array1.elementAt(i) )
    {
        array2.add( array1.elementAt(i) );
    }   
}

所以你可以在循环中的测试上设置一个断点,看看接下来会发生什么。(我知道有更好的方法来写这个;这只是为了说明这一点。)

在像 Ruby 这样的语言中,惯用风格似乎有利于更高级别的单行编码,例如来自http://rubyquiz.com/quiz113.html

quiz.to_s.reverse.scan(/(?:\d*\.)?\d{1,3}-?/).join(',').reverse

我想知道您是否可以提出任何有效的调试技术,例如,如果您更改了正则表达式......您是否仍会使用传统的调试器,并进入/跳过链式方法?或者,还有更好的方法?

谢谢!

4

3 回答 3

3

如果我要调试您的示例,我要做的第一件事就是将其分解为多个步骤。我不在乎它是“pythonic”还是“ruby 方式”或“tclish”或其他什么,这样的代码可能很难调试。

这并不是说我不写那样的代码。一旦它被调试过,有时将它全部加入一行是可以的,但我发现自己更倾向于可读性和可维护性,而不是编写简洁的代码。如果单行方法确实更具可读性,我会使用它,但如果不是,我不会。

于 2009-09-14T16:48:35.487 回答
2

将多个动作组合成一行是很好的,当您仍然可以查看有问题的行并知道它将完全按照您想要的方式执行时。当您无法查看代码并说“是的,好的,它可以 xyz,它不可能不能”的那一刻,您应该考虑将其分解为单独的部分。

我给那些有长过程/方法的人同样的建议。如果您无法查看代码并确切地知道它在所有情况下都在做什么,那么请将其分解。您可以将每个“非显而易见”的代码片段分解为它自己的方法,并单独为该片段编写测试。然后,您可以在原始方法中使用该方法并知道它会起作用……而且您的原始方法现在更容易理解。

同样,您可以将“scan(/(?:\d*.)?\d{1,3}-?/)”代码分解为另一种方法并自行测试。然后原始代码可以使用该方法,并且应该更容易理解并知道它正在工作。

于 2009-09-14T16:52:51.973 回答
0

如果我必须调试您发布的那一行,我发现没有什么能比将它分解成独立的语句更有帮助。这样您就可以看到每个方法作为参数接收的内容,以及它返回的内容。

这样的语句使代码难以维护。

于 2009-09-14T16:51:33.613 回答