在新行上列出每个函数/方法参数是一个坏主意,为什么?


22

我与某人合作,每当他们调用一个函数时,他们会将参数放在换行符上,例如

aFunction(
    byte1,
    short1,
    int1, 
    int2,
    int3,
    int4,
    int5
) ;

我觉得这很烦人,因为这意味着代码不是很紧凑,因此我必须上下扫描更多内容才能真正理解逻辑。我很想知道这是否真的是不好的做法,如果是,我如何说服他们不要这样做?


25
+1,我不了解您的问题,但我也很讨厌。但是,如果函数中有很多参数,那么您的函数可能做得太多。
maple_shaft

28
更重要的是,为什么我们仍然必须看到彼此对此的偏好?为什么我们的IDE不能以我们想要的任何样式自动显示它?
Alex Feinman

5
迈克,我喜欢让代码占用最少的屏幕空间。但这是一个折衷。我将{放在单独的行上,因为它可以更轻松地与结束}匹配并正确理解该块的范围。失去一系列屏幕房地产值得权衡。
布赖恩·施罗特

2
@Alex:你完全正确。我认为正确的做法是使用一种语言,其中代码的解析树存储在磁盘上,并根据用户的喜好进行显示。
Neil G

1
@maple_shaft我鄙视这样的声明。不是因为没有任何道理,而是因为有太多的人遵循这样的建议而没有留下任何细微差别的空间。
Stijn

Answers:


38

这只是您可能喜欢或不喜欢的编码指南。重要的是您和您的同事同意使用或不使用它。

显然,提高可读性的最佳方法是限制参数的数量。


24
太多的人通过将参数转储到数组中来减少参数。我宁愿看到一个丑陋的烂摊子,也不愿看似具有隐藏复杂性的简洁代码。
Satanicpuppy

18
数组不是要走的路。args中可能隐藏了一个结构,或者该函数执行了太多操作,应该拆分。
Michael K

4
我发现使用多行代码有助于使代码可读IF参数是长表达式还是少数几个。否则,这很烦人。
PedroC88 2011年

3
将它们放在数据传输对象中只会解决问题。如果所有参数都是必需的,那么它们都必须是DTO构造函数的必需参数,这意味着您仍然有那么多参数。
Scott Whitlock

21

这是一个偏好问题。对于要在其中记录每个参数的复杂函数调用,或者在变量相当长且变量很多的地方,这可能会很好。

例如:

do_complex_op(
      0, //Starting state, always 0, ask Joe why
      X, //X-coord of thingy
      y, //Y-coord of thingy
      73, //in this case, we don't want to use Z but want constant 
      dlogMessageTitle, //message for dialogue title
      dlogMessageText, //message for dialogue contents, don't care about this.
      SomethingIP, //IP of something-or-other server, can be NULL, won't crash.
      someObject.childObject.getValue(key1).HVAL, //very long path to HVAL
      someObject.childObject.getValue(key1).LVAL, //very long path to LVAL
      this.parentWindow.owner.mainTextBox.text.value.trim, //get the trimmed text, untrimmed text causes weird output
      pvrMainSettingForLongBlahs.getObjectByPath(somePath),
      pvrMainSettingForLongBlahs.K_TCA_UPPER_LIMIT,
      pvrMainSettingForLongBlahs.K_ENDPOINT_COMPLIANCE_LEVEL,
 );

对于允许使用命名参数的语言,如果使用参数名称(在PL / SQL中为示例),则这种情况更为常见:

PKG_SOME_TEST_CODE.FN_DO_SOMETHING( in_text => 'test text',
                                    in_id => v_id,
                                    in_ref_id => v_ref_id,
                                    out_array_for_storage => v_bArray); 

但是我同意您的观点,如果函数调用简单且参数太多,这可能会很烦人,例如:

setColour (
    r,
    g,
    b
 );

我发现更容易阅读为

 setColour(r,g,b);

对于@ammoQ:

rc=a(b,c(d,e(f)))

rc=a(
     b,
     c(
       d,
       e(
         f
        )
      )
    )

11
第一个例子是对一个实际问题的错误答案。为什么不首先使用显式变量anmes?
deadalnix11年

@deadalnix:好点,把它清理了一下。
FrustratedWithFormsDesigner

1
真正。但是,变量名称并不总是一个问题。它与长变量名,具有默认值的参数等等有关
inspectorG4dget

4
我认为解决该问题的更好方法是重构do_complex_op(),使其采用结构作为参数。然后您可以做do_complex_op(new paramStruct { StartingState = 0, XCoord = xcoord }),然后它变得可以自我记录并且更容易阅读
KallDrexx 2011年

1
@KallDrexx:我同意,但是有时不能更改代码,例如当它是别人库中的函数时。当然,我可以对其进行包装,但是在某些时候我仍然必须调用其原始函数。
FrustratedWithFormsDesigner

10

国际海事组织(IMO)所有不常见的东西都是不好的做法,除非可以肯定地证明它比通常的样式优越。“品味的东西”是编写代码的可怜借口,比大多数程序员所需要的要难读,因为有一天,一个不习惯这种风格的可怜的灵魂将不得不维护该代码。

证明它不常见相对容易,显示MSDN或类似网站中的示例源,显示大型开源代码库等。显示代码美化器的输出。最终,展示如何在感到沉沦还有的团队在做。不要因为别人太固执而接受不良的风格。


嗯...采用这种方法,我们如何才能引入新的最佳实践(或者从语法上正确的话:更好的实践)?
Treb 2011年

2
Treb:当然,只是表明更好的实践实际上更好,而不仅仅是不同
user281377 2011年

4
但是,“难于阅读”本身是主观的并且是见解的。对我而言,每行一个参数比每行两个,三个或四个参数在视觉上更容易解析。如果调用超出了编辑器中大约100个字符的标记,我总是将其分成多行。
Toby

2
可以客观地衡量“阅读困难” 。只是没有。争论起来更有趣。
JasonTrue 2011年

1
它可以客观地测量,但不能独立于阅读者。
jk。

9

好吧,这里有一些诱饵。我从来没有被指控做流行的事情。显然,如果事物适合于一行,那么就可以将它们适合于一行。

但是我主要关心的不是代码是“丑陋”还是“漂亮”。我主要关心的是理解和进行更改而不犯错误的难易程度。

如果参数很长并且有很多参数,为什么不将它们放在单独的行上呢?在我看来,这使得更容易查看它们是什么,并且在需要时更容易对其进行更改。如果需要的话,它还给我留出了空间,可以对每个参数附加评论。

我还想最大程度地减少在函数中添加或删除参数时出错的可能性,这种情况更可能发生在参数列表的末尾而不是开头。因此,我宁愿将逗号(,)放在行的开头,而不是结尾。然后,例如,如果我想在列表的末尾删除或添加一个参数,那就是单行编辑。我不必摆弄所有行末尾的逗号,而最后一行必须以括号结尾。

所以(男孩,我会为此而被激怒)我是这样写的:

nameOfFunction(firstArgument
    , secondArgument // optional comment
       ...
    , lastArgument   // optional comment
    );

当一个函数有五个到二十个参数时,该函数不会一次全部获得。随着时间的流逝,这意味着需要进行大量编辑。任何未完成的编辑是语法错误或错误。所以我不认为这很漂亮。我声称它有助于正确进行编辑。

(对于那些说我应该传递结构的人,所有要做的就是替换问题,因为您需要一堆代码来填充结构,更不用说额外的代码来声明和分配它了。)


1
我个人认为这是一个很好的答案,因为您很好地解释了自己的推理。干得好迈克。
乔丹

8

我也不会这样。我工作过的最佳实践通常是将函数调用全部放在一行上,除非您必须水平滚动任何数量以查看整个调用。这是一个判断电话,但我可以肯定地说,除非您的组织建立了标准,否则将这样的所有功能置于不合时宜的状态。

这就是为什么对组织来说,好的做法是建立一套所有程序员都应该遵循的指南。其全部有关一致性和可读性。


5

它使得更容易:

  • 重新排列参数。
  • 注释掉或禁用参数。
  • 在版本控制系统中查看差异时,准确查看更改了哪个参数
  • 添加或删除参数或更改函数名称时,请避免对所有内容进行缩进和自动换行。(即使您的编辑器自动缩进,您仍在创建许多无用的空格更改,这使得在版本控制系统中进行更改变得更加困难。)

4

我要说的是,函数调用应该全部放在一行上,除非它们大大超出了标准代码宽度(通常为80个字符,通常是引起参数的原因:-)。

我认为这种风格没有任何优势。它主观上看起来很丑陋,我在搜索代码时感到很痛苦。例如,您可能想快速搜索并查看是否曾经使用传递为NULL的特定参数来调用该函数。当所有参数都在一行上时,这在视觉上很容易,而在像这样拆分它们时则更难。


这80个字符的东西必须走,只是没有任何技术上有效的理由了。现在,我们生活在19xx X 16xx显示器,可调字体和字体大小的时代。
匿名

4
@anon:这样做的正当理由吗?您为什么认为文本打印在列中,书本比它们窄?因为当跨过很长的线阅读时,人眼会失去跟踪。
Zan Lynx

4
@anon:我也喜欢用宽屏在水平方向上打开两个或三个文件,然后一行返回80-100个字符。
Zan Lynx

4
@anon:从技术上说不,实际上:是的。Zan Lynx是完全正确的,另外还有其他原因:合并,比较,使用命令行实用程序...哦,祝您好运,随着年龄的增长,您会专注于8p字体:o)
MaR

3

我经常在函数声明定义中看到该样式,但从未在调用中看到(直到现在)。有时这很有意义,因为它使您可以更清楚地为单个参数添加注释。好像他在没有真正了解其背后的根本原因的情况下将该样式复制到了呼叫中。您有一个很好的论据,而他似乎没有一个很好的论据,所以您有我的一票,但我不是您必须说服的人。


我在通话中都看到了。如果参数列表太长,则应将其分成多行。如果参数不在宽度限制内正常分组,我希望它们在单独的行上。如果函数和参数名称在一行中很好地匹配,那么我经常看到它们以这种方式排列。
BillThor 2011年

2

是否违反公司编码标准?

如果不是,请启动有关标准以及人们希望看到的变化的讨论。确保将此作为您要更改的事情之一提出。

全面讨论为什么您认为这没有用,并希望您能赢得胜利。您永远都不知道您的同事可能会说服您,毕竟他的方式是最好的;)

一旦有了更新的标准,它就会记录每个人都应该编码的内容,因此,如果您的同事坚持这样做,则可以在他的代码审查中提出。


2

它对您来说看起来可能很时髦,但它使编写代码更加容易。重构时,您可以轻松注释掉各个参数,并在实际删除内容之前检查重构。您也可以注释掉并临时替换类型。

它比以下内容还容易阅读:

int f(int, int, int,
      char, double, int
      X const&, Y)
{}

我并没有像您展示的那样极端(由于参数上没有名称,因此使用不多),但是我已经习惯了将每个参数拆分成一行,或者根本不拆分。

重要的是您的代码可以在标准的80col显示器上打印或显示,并且仍然清晰易读。


2

对于这样的事情,您几乎不会从程序员那里得到诚实的答案。每个人都会回答自己喜欢或不喜欢的事情。事实是,尽管我们所有人有时都在为此挣扎,但唯一的“坏习惯”是您自己的僵化。

您必须对自己残酷诚实,才能区分出实际上是不好的事情和只是让您烦恼的事情。事实是,在C / C ++和类似语言中,您很少会发现对代码的可理解性有明显影响的缩进实践。关于这类事情的大多数讨论只是双方都堆满了人们提出荒谬,虚假的论据,试图证明自己的个人喜好是正当的。

在我的阅读中……这正是您在这个问题上的要求:一个荒谬,虚假的论据,用以证明您的个人喜好。


0

老实说,这取决于人。.我要说的是FrustratedWithForms的第一个示例所演示的复杂功能,然后是。否则很大。再次,这就是为什么我更喜欢任意应用代码的IDE功能。


0

“我很想知道这是否真的是不好的做法……”

是的,这是不好的做法,除非变量列表异常长。但是在那种情况下,问题可能出在功能的设计上。为什么不传递封装了许多参数的对象?

“……如果是的话,我该如何说服他们不要这样做?”

绑住他们,继续挠他们,直到他们同意停止这种胡扯。


“为什么不传递封装了许多参数的对象?” 好的,现在您已将问题移至该新对象。它仍然需要相同数量的参数(例如,通过其构造函数),因此您仍然遇到相同的问题。
Stijn

-2

您为什么要在如此琐碎的问题上浪费时间?只需启动您可信赖的IDE,打开文件,然后重新格式化即可。瞧!它将采用您想要的任何形式。

现在让我们继续讨论真正重要的问题-vi或emacs,大声笑。


然后,当您将其检查到源代码控制中时?
pdr

-2

我要说的是,如果参数只适合一行,那就这样做。如果没有,那么每行一个参数可以提高可读性。

foo(arg1, arg2, arg3, arg4, arg5)

foo(
    arg1=arg1,
    arg2=arg2,
    arg3=arg3,
    arg4=arg4,
    arg5=arg5,
    arg6=arg6,
    arg7=arg7
)

3
这似乎并没有提供任何实质性的制作上分和14分之前解释的答案
蚊蚋
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.