9

这不是一场圣战,这不是“哪个更好”的问题。

对单个语句 if 块使用以下格式的优点是什么。

if (x) print "x is true";

if(x) 
    print "x is true";

相对于

if (x) { print "x is true"; }
if(x) {
    print "x is true";    
}

如果你格式化你的单个语句 ifs 没有括号或知道一个程序员这样做,是什么导致你/他们首先采用这种风格?我对这给你带来了什么好处特别感兴趣。

更新:由于最受欢迎的答案忽略了实际问题(即使它提出了最理智的建议),这里是无括号专业人士的综述。

  1. 紧凑
  2. 对某些人来说更具可读性
  3. 括号调用范围,在某些情况下具有理论上的开销
4

42 回答 42

51

我发现这个:

if( true ) {
    DoSomething();
} else {
    DoSomethingElse();
}

比这更好:

if( true )
    DoSomething();
else
    DoSomethingElse();

这样,如果我(或其他人)稍后返回此代码以向其中一个分支添加更多代码,我将不必担心忘记将代码括在大括号中。我们的眼睛会在视觉上将缩进视为我们正在尝试做的事情的线索,但大多数语言不会。

于 2008-09-18T22:11:01.863 回答
48

我非常不喜欢任何将 if 的测试和正文放在同一行的样式。

这是因为共享行使得在许多调试器中无法在 if 的主体上设置断点,因为断点通常基于行号。

于 2008-09-18T22:09:31.073 回答
34

总是使用大括号是个好主意,但标准答案总是给出“如果有人添加一行代码并忘记添加大括号怎么办?” 是一个相当薄弱的理由。

有一个微妙的错误可以通过从一开始就没有大括号来引入。这在我身上发生过几次,我也看到它发生在其他程序员身上。

它从一个简单的 if 语句开始,很天真。

if (condition)
    do_something();
else
    do_something_else();

这一切都很好。

然后有人出现并在 if 中添加了另一个条件。他们无法使用 && 将其添加到 if 语句本身,因为逻辑不正确,因此他们添加了另一个 if。我们现在有:

if (condition)
    if (condition2)
        do_something();
else
    do_something_else();

你看到问题了吗?它可能看起来正确,但编译器的看法不同。它是这样看的:

if (condition)
    if (condition2)
        do_something();
    else
        do_something_else();

这意味着完全不同的东西。编译器不关心格式。else 与最近的 if 一起使用。另一方面,人类依赖于格式化,很容易错过这个问题。

于 2008-09-19T01:13:55.187 回答
21

我总是用

if(x) 
{
    print "x is true";    
}

省略大括号可能会导致维护代码的人错误地认为如果他们在当前行之后添加一行,他们正在添加到 if 子句。

于 2008-09-18T22:11:15.187 回答
14

我用

如果 (x)
{
    做点什么();
}

对于多行,但我更喜欢无括号的单行:

如果 (x)
   做点什么();
别的
   DoSomethingElse();

我发现多余的括号在视觉上令人反感,而且我从来没有犯过上述错误之一,在添加另一个语句时不添加括号。

于 2008-09-18T23:06:31.467 回答
8
if
{
// code
}
else 
{
// else code
}

因为我喜欢代码块排成一行(包括它们的大括号)。

于 2008-09-18T22:11:35.997 回答
7

如果我编码:

if(x) 
    print "x is true";

并且 6 个月后需要添加一个新行,大括号的存在使我输入的可能性大大降低

if(x) 
    print "x is true";
    print "x is still true";

这将导致逻辑​​错误,而不是:

if(x) { 
    print "x is true";
    print "x is still true";
}

因此,我发现花括号使此类逻辑错误更易于阅读和避免。

于 2008-09-18T22:14:02.030 回答
7

像马特(上面的 3 个)一样,我更喜欢:

if (x)
{
    ...statement1
    ...statement2
}

if (x)
    ...statement
else
    ...statement

我认为认为有人可能稍后出现并且没有意识到他们必须添加大括号以形成多行 if 块是很奇怪的。如果这超出了他们的能力,我想知道还有什么!

于 2008-09-18T23:14:23.973 回答
5

单语句 if 块缺少大括号:

优点:

  • 更少的字符
  • 更清洁的外观

缺点:

  • 均匀性:如果块看起来相同,则并非所有
  • 向块中添加语句时可能出现错误:用户可能忘记添加大括号,新语句将不会被 if 覆盖。

如:

if(x) 
    print "x is true";
    print "something else";
于 2008-09-18T22:17:17.327 回答
5

当我在函数开头测试中断条件时,我倾向于只使用单行代码,因为我喜欢让这段代码尽可能简单和整洁

public void MyFunction(object param)
{
     if (param == null) return;

     ...
}

另外,如果我发现我确实想避免使用大括号并内联 if 子句代码,我可以将它们单行,这样对于任何在 if 需要添加括号的人添加新行的人来说都是显而易见的

于 2008-09-18T23:14:22.197 回答
4

我用

if (cond) {
  ...
} else {
  ...
}
  • 一切都应该总是有大括号。即使现在我在 if 块中只有一行,我稍后也会添加更多。
  • 我不会把大括号放在他们自己的线上,因为这是毫无意义的浪费空间。
  • 为了便于阅读,我很少将块与条件放在同一行。
于 2008-09-18T22:14:52.743 回答
4

Joel Spolsky写了一篇很好的文章:让错误的代码看起来是错误的

他专门解决了这个问题……

if (i != 0)  
    foo(i);

在这种情况下,代码是 100% 正确的;它符合大多数编码约定并且没有任何问题,但是 if 语句的单语句体没有括在大括号中的事实可能会困扰您,因为您可能在脑后思考,天哪,某人可能会在那里插入另一行代码

if (i != 0)
    bar(i);
    foo(i);

…忘记添加大括号,从而意外地使 foo(i) 成为无条件的!因此,当您看到不在大括号中的代码块时,您可能会感觉到一点点的不干净,这让您感到不安。

他建议你……

... 故意以这样一种方式构建您的代码,使您对不洁的嗅觉使您的代码更有可能是正确的。

于 2008-09-18T22:34:19.953 回答
4

我不喜欢在不需要时使用大括号。我觉得它使方法中的行数膨胀并使其不可读。所以我几乎总是选择以下内容:

if (x)
   print "x is true"
for (int i=0; i<10; i++)
   print "y is true"

等等。如果有人需要添加另一个语句,那么他可以添加大括号。即使你没有 R# 或类似的东西,这也是一笔小买卖。

尽管如此,在某些情况下,即使语句中只有一行,我也会使用大括号,那就是如果该行特别长,或者如果我需要在那个“if”中添加注释。基本上,我只是用我的眼睛看起来更好看的东西。

于 2008-09-18T23:14:35.347 回答
3

空白是你的朋友....

但是,话又说回来,我喜欢:

if (foo)
{
    Console.WriteLine("Foobar");
}
于 2008-09-18T22:10:50.227 回答
3

说真的,你最后一次在任何地方的任何代码中出现导致某人这样做的错误是什么时候:

if (a)
  foo();
  bar();

是的,从不……*这里唯一真正的“专业”就是匹配周围代码的风格,而将审美之争留给刚从大学毕业的孩子们。

*(警告当 foo(); bar(); 是宏扩展时,但这是宏的问题,而不是大括号的问题/ ifs。)

于 2008-09-18T23:14:12.883 回答
3
if (x) {
    print "x is true";    
}
else {
    do something else;
}

我总是打大括号。这只是一个好习惯。与思考相比,打字不是“工作”。

注意条件句前的空格。这有助于它看起来不像一个方法调用。

于 2008-09-18T23:45:15.803 回答
3

另一种方法是写:

(a==b) ? printf("yup true") : printf("nop false");

如果您想存储一个比较简单条件的值,这将是实用的,如下所示:

int x = (a==b) ? printf("yup true") : printf("nop false");
于 2015-03-04T19:41:54.807 回答
2
if (x)
{
    print "x is true";
}

在同一列中打开和关闭大括号可以轻松找到不匹配的大括号,并在视觉上隔离块。在与“if”相同的列中打开大括号可以很容易地看出该块是条件的一部分。由仅包含大括号的行创建的块周围的额外空白使得在浏览代码时很容易挑选出它的逻辑结构。当人们稍后编辑代码并误读哪些语句是条件的一部分而哪些不是时,总是显式地使用大括号有助于避免问题 - 缩进可能与现实不符,但用大括号括起来总是会的。

于 2008-09-18T22:15:10.497 回答
2

大约唯一一次似乎接受无支撑是在方法开始时检查参数时:

public int IndexOf(string haystack, string needle)
{
    // check parameters.
    if (haystack == null)
        throw new ArgumentNullException("haystack");
    if (string.IsNullOrEmpty(needle))
        return -1;

    // rest of method here ...

唯一的好处是紧凑。当很明显:

  • 该方法在任何真正的分支上退出
  • 很明显,这些都是 1-liner

也就是说,出于其他人所述的原因,我将始终{} 用于程序逻辑。当您放下大括号时,很容易在没有大括号的情况下精神上支持并引入微妙的代码缺陷。

于 2008-09-19T05:33:51.660 回答
2

H8ers 该死的我不是一个真正的教条规则的人。在某些情况下,如果它没有超过一定的宽度,我实际上会支持紧凑性,例如:

if(x > y)      { xIsGreaterThanY(); }
else if(y > x) { yIsGreaterThanX; }
else           { xEqualsY(); }

这对我来说比以下更具可读性:

if( x > y ){
    xIsGreaterThanY(); 
}else if( x < y){
    yIsGreaterThanX();
}else{
    xEqualsY();
}

这具有鼓励人们将逻辑抽象到方法中的额外好处(就像我所做的那样),而不是将更多逻辑集中到嵌套的 if-else 块中。它也占用了三行而不是七行,这可能使得不必滚动即可查看多个方法或其他代码。

于 2016-06-07T10:20:16.677 回答
1

我更喜欢括号样式,主要是因为它给眼睛一个清晰的起点和终点。它使查看语句中实际包含的内容变得更容易,并且它实际上是一个 if 语句。也许是一件小事,但这就是我使用它的原因。

于 2008-09-18T22:14:35.303 回答
1

只要它在你工作的团队中是一致的,那么这并不重要

每个人都做同样的事情是主要的

于 2008-09-18T22:14:49.780 回答
1

如果您(或其他维护或更改代码的编码人员)需要在该条件块的某些部分添加语句,则将您的单行 if 语句括起来具有相当大的理智优势,可以保护您免受头痛。

于 2008-09-18T22:15:16.067 回答
1

不管怎样,这就是我要走的路!它看起来最好。

If(x)
{
    print "Hello World !!"
}
Else
{
    print "Good bye!!"
}
于 2008-09-18T22:19:18.210 回答
1

如果您对各种代码格式样式的名称感到好奇,维基百科有一篇关于缩进样式的文章。

于 2008-09-18T22:25:08.553 回答
1

如果你做这样的事情:

if(x)
{
    somecode;
}
else
{
    morecode;
}

这对于长期存在的代码的源代码控制和预处理器指令效果更好。添加#if 左右会更容易,而不会无意中破坏语句或不必添加额外的行。

习惯了有点奇怪,但一段时间后效果很好。

于 2008-09-18T22:49:16.563 回答
1

如果它是 if 的一行(以及可选的 else 行),我宁愿不使用括号。它更具可读性和简洁性。我说我更喜欢它,因为这纯粹是一个偏好问题。尽管我认为试图强制执行必须始终使用大括号的标准有点愚蠢。

如果您不得不担心有人在 if 语句的主体中添加另一行而不添加(仅需要)大括号,我认为您的问题比次拜占庭编码标准更大。

于 2008-09-18T23:24:51.093 回答
1
/* I type one liners with brackets like this */
if(0){return(0);}
/* If else blocks like this */
if(0){
    return(0);
}else{
    return(-1);
}

我从不在制表符之外使用多余的空格,但总是包含括号可以节省大量时间。

于 2008-09-19T04:21:40.680 回答
1

我不喜欢在同一行使用以下关键字的右大括号:

如果 (x) {
    打印“x 为真”;    
} 别的 {
    做点别的事情;
}

这使得仅删除/注释掉 else 子句变得更加困难。通过将 follow 关键字放在下一行,我可以利用编辑器,例如,让我选择一系列行,并一次注释/取消注释它们。

如果 (x) {
    打印“x 为真”;    
}
//别的 {
// 做其他事情;
//}
于 2008-09-30T20:10:00.507 回答
1

我总是喜欢这个:

if (x) doSomething();

if (x) {
    doSomthing();
    doOtherthing();
}

但始终取决于您正在执行的语言和操作。有时我喜欢戴牙套,有时不喜欢。取决于代码,但我编码就像必须写一次,重写十次,读一百次;所以,随心所欲地去做,就像你想更快地阅读和理解一样

于 2008-09-30T20:14:57.187 回答
0

对我来说,大括号更容易看到程序的流程。它还可以更轻松地将语句添加到 if 语句的主体。当没有大括号时,您必须添加大括号才能添加另一个语句。

我想不使用大括号的优点是它看起来更干净,而且你不会浪费一条带右大括号的线。

于 2008-09-18T22:12:53.483 回答
0

行间距和缩进对可读性有很大帮助。

就可读性而言,我更喜欢以下内容:

// Do this if you only have one line of code
// executing within the if statement
if (x)
    print "x is true";

// Do this when you have multiple lines of code
// getting executed within the if statement    
if (x)
{
    print "x is true";
}
于 2008-09-18T22:13:40.407 回答
0

我希望 IDE 会强制执行这种行为。正如您正确指出的那样,没有“正确”的行为。一致性更重要……它可以是任何一种风格。

于 2008-09-18T22:56:59.740 回答
0

到目前为止,我觉得自己的投票被否决了,但我会保证以下之一:

if (expr) {
   funcA();
}
else {
   funcB();
}

或者,在有限的情况下为了可读性而简写:

if (expr) funcA();
else funcB();

对我来说,当您希望它像英语语法一样阅读时,速记格式很好。如果代码看起来不够可读,我将换行:

if (expr)
   funcA();
else
   funcB();

经过仔细考虑,我不会在if/else块中放置嵌套条件以避免编码器/编译器的歧义。如果它比这更复杂,我在ifelse块上都使用大括号。

于 2008-09-19T01:29:39.547 回答
0

这种类型的任何格式都可以。人们会在这个问题上与你争论不休,因为它很容易理解。人们喜欢谈论他们理解的事情,而不是处理更大的问题,比如好的设计和用新算法解决难题。对于简单的单行,我倾向于不使用括号。但是,我也很高兴用括号来阅读它。如果给定项目有特定的样式指南,我更愿意遵循它。我相信对正确性的一些主观理想的一致性。

我个人对单行不加括号的选择是由于键入的字符更少、代码更短且简洁。

于 2008-09-19T05:54:02.593 回答
0

在提供的选项中,我会选择

if (x) {
  print "x is true";    
}

仅仅因为大括号是打字的习惯。

但实际上,作为一个主要使用 Perl 的程序员,我更有可能使用

print "x is true" if x;

(当我使用不支持后缀条件的语言时,这总是让我感到困惑。)

于 2008-09-19T15:52:45.983 回答
0

我更喜欢不带括号的单行语句,我知道插入新代码行时可能会忘记添加它们,但我不记得上次发生这种情况是什么时候。我的编辑器(vim)阻止我写这样的东西:


if (x)
    x = x + 1;
    printf("%d\n", x);

因为它会以不同的方式缩进。我唯一遇到的问题是写得不好的宏:


#define FREE(ptr) {free(ptr); ptr = NULL;}

if (x)
    FREE(x);
else
    ...

这当然行不通,但我认为最好修复宏,以避免那些可能的错误或问题,而不是更改格式化样式。

因此,这种格式化方式可能存在问题,但它们并不是致命的。它最终成为一个品味问题。

于 2008-09-20T23:21:28.160 回答
0

我还没有看到有人提到将括号与 emacs 中的 if -- 括号匹配放在同一行的最有用的原因。当您将光标放在结束括号上时,emacs 会显示带有匹配开始括号的行。将开始括号放在自己的行上,否定该功能。

于 2008-09-23T01:19:04.567 回答
0

我更喜欢以下...我认为它看起来更干净。

if(x)
{
    code;
}
else
{
     other code;
}
于 2008-09-23T01:43:31.093 回答
0

我想我比我想象的更离群。我还没有注意到这个。

我是

if (x)
{ foo(); }

它感觉紧凑且可读(我讨厌大括号),但它使条件的范围明确。

它也比单行 if 对断点更友好。在我的大括号换行符世界中,它也让我感觉更自在:

if (x)
{ foo(); }
else
{
   bar();
   baz();
}

编辑:看来我误读了原始问题,所以这个答案离题了。不过,我仍然对任何回应感到好奇。

于 2009-07-10T04:52:11.613 回答
0

一个衬垫就是……一个衬垫,应该保持这样:

if (param == null || parameterDoesNotValidateForMethod) throw new InvalidArgumentExeption("Parameter null or invalid");

例如,我喜欢这种用于参数检查的风格,它紧凑且通常易于阅读。我过去一直使用带有缩进代码的大括号,但发现在许多微不足道的情况下它只是浪费了显示器上的空间。在某些情况下放下大括号使我能够更快地进入方法的实质,并使整体呈现更容易在眼睛上。但是,如果它涉及更多,那么我会像对待其他所有事物一样对待它,并且会像这样全力以赴:

if (something)
{
    for(blablabla)
    {
    }
}else if
{
 //one liner or bunch of other code all get the braces
}else
{
  //... well you get the point
}

话虽这么说...我鄙视同一行的大括号,如下所示:

if(someCondition) { doSimpleStuff; }

最坏的

if(somethingElse){
  //then do something
}

它更紧凑,但我发现很难跟踪牙套。

总的来说,这更像是个人品味的问题,只要一个人不采用某种非常奇怪的方式来缩进和支撑......

    if(someStuff)
        {
  //do something
        }
于 2009-07-10T05:21:48.497 回答
0

我相信这是最重要的原因,我很惊讶地看到它还没有作为答案给出(尽管它已经在评论中提到,在答案中的脚注和答案中旁白))。

你应该总是使用括号,因为

if (x)
   DoSomething();

DoSomething如果随后被重新定义为多语句宏,则中断:

#define DoSomething()          语句1 ;   声明2

当然,我们都知道正确的做法是像这样定义宏:

#define DoSomething()    做 {  语句1 ;  声明2} 而 (0)
这使得宏的行为更像是一个语句。

也就是说,我承认我没有听从自己的建议。当我有(看起来是)单个语句时,我通常不使用大括号。(羞愧地低着头。)

于 2017-08-22T22:59:08.170 回答