大家写代码时喜欢用 Guard Clause 还是一条路径走到底? - V2EX
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
请不要在回答技术问题时复制粘贴 AI 生成的内容
agagega
V2EX    程序员

大家写代码时喜欢用 Guard Clause 还是一条路径走到底?

  •  
  •   agagega 2018-07-03 01:00:52 +08:00 5735 次点击
    这是一个创建于 2727 天前的主题,其中的信息可能已经有所发展或是发生改变。

    前两天 Code Review 的时候被指出了这个问题。

    如题,是

    bool func() { if (xxx) return false; if (xxx) return true; xxx; return true; } 

    还是

    bool func() { if (xxx) { if (xxx) return false; else return true; } else { xxx; return true; } } 

    好像前者一般比较清爽,缩进层次也少。我只看过王垠在他的博客里强烈支持过第二种。

    32 条回复    2018-07-04 10:09:18 +08:00
    blueskit
        1
    blueskit  
       2018-07-03 01:02:58 +08:00 via Android
    王垠为什么支持呢?
    VVVVVEX
        2
    VVVVVEX  
       2018-07-03 01:08:31 +08:00   1
    你给的两个例子,逻辑都不一样。
    至于使用那种形式,还是看逻辑啊。
    如果是并列条件,使用第一种,如果是前提条件,使用前套逻辑。这样的代码符合人类的思维,好懂。
    王垠又不是啥权威,写文章很多,无论是工业产品,还是开源项目,并没有什么建树,并不觉得他说什么就有道理。
    我觉得除了 80 列是个铁律,别的都不是完全的定死的。
    df4VW
        3
    df4VW  
       2018-07-03 01:26:10 +08:00   2
    Guard 有时候会因为逻辑 上没思考全导致部分条件没有覆盖而进入之后的代码流程,强制 if else 2 分能确保覆盖所有情况,养成习惯之后能保证处理到所有 case,不管是有意还是无意。再加上王垠用的是 java,用 if else ide 能提示有些 case 没处理

    用这种习惯之后几乎没有负担的被动技能来减少代码出错的可能性其实也是比较务实的做法
    1010011010
        4
    1010011010  
       2018-07-03 03:07:23 +08:00
    我喜欢第一种,过程比较清晰
    sugarsalt
        5
    sugarsalt  
       2018-07-03 03:16:21 +08:00
    case 多的话,switch
    lightening
        6
    lightening  
       2018-07-03 04:29:37 +08:00
    代码首先要反映程序员的逻辑,怎么想就怎么写。

    两种常见情景:

    1 )写到这里,哎呀这个变量如果是 b 就不对了,先 return 掉2 )写到这里,发现有以下两种可能的情况

    显然 1 )应该用 early return,2 )应该用 if else
    watzds
        7
    watzds  
       2018-07-03 07:00:54 +08:00 via Android
    @VVVVVEX 80 列算什么铁律,那是以前的显示器一行只能显示这么多,现在 120 也没问题
    tamlok
        8
    tamlok  
       2018-07-03 08:16:03 +08:00 via Android
    @watzds 左右分屏的时候你就知道 80 好还是 120 好。而且 80 还有另一个意义,间接地控制代码的嵌套层级。
    jatesun
        9
    jatesun  
       2018-07-03 08:44:30 +08:00
    第一种,第二种可读性不高
    jorneyr
        10
    jorneyr  
       2018-07-03 08:46:12 +08:00
    bool func() {
    if (xxx) { return false };
    if (xxx) { return true };
    xxx;
    return true;
    }
    Nick66
        11
    Nick66  
       2018-07-03 08:52:48 +08:00
    一会简写一会不简写最恶心
    whileFalse
        12
    whileFalse  
       2018-07-03 08:56:17 +08:00   1
    if (xxx) return false;
    else return true;

    这个代码太骚了。
    VVVVVEX
        13
    VVVVVEX  
       2018-07-03 09:00:29 +08:00
    GCC LLVM
    Linux *BSD
    QEMU
    Python Django
    node
    Vim
    Firefox Chrome
    React
    Rust
    这些项目都是遵循 80 列,有比 90 后年龄大的,也有比 90 后年轻的。
    别的项目我不太清楚,gayhub 上的总会有很多超过 80 列的个人项目,数量上一定是取胜的。
    crayygy
        14
    crayygy  
       2018-07-03 09:19:25 +08:00 via iPhone
    就你提供的代码风格来看,这第二种写出来会被打的...不管哪种语言,if else 还是尽量都应该括号保证有合理的 scope,也方便以后添加逻辑,除非是保护性的代码,if ==null return 这种我觉得不需要括号,直接一行话搞定。
    liuxey
        15
    liuxey  
       2018-07-03 09:25:33 +08:00
    第二种是真的神奇,一会有括号,一会没括号,而且逻辑和第一个也不一样,我更喜欢 #10 的写法
    sagaxu
        16
    sagaxu  
       2018-07-03 09:31:41 +08:00 via Android
    10 个变量二分就是 1024 种组合,来个 10 层嵌套吗?

    形式上的完整覆盖,和逻辑上的完整覆盖,目的是哪个?
    chenyu8674
        17
    chenyu8674  
       2018-07-03 09:42:04 +08:00
    跟代码没关系,本质上还是看写代码的人怎么理解这段判断关系
    zarte
        18
    zarte  
       2018-07-03 09:48:43 +08:00
    第二种,
    只返回一个的时候第一种
    watzds
        19
    watzds  
       2018-07-03 09:53:45 +08:00 via Android
    @tamlok 我不觉得 120 就比 80 好,只是觉得这不是铁律
    qY3209HZitEb5Zty
        20
    qY3209HZitEb5Zty  
       2018-07-03 09:58:02 +08:00
    ```
    bool func() {
    if (xxx) {
    return xxx ? false : true;
    }

    xxx;
    return true;
    }
    ```
    Chieh
        21
    Chieh  
       2018-07-03 10:18:53 +08:00 via Android
    原则上用第二种,如果较短的 if else 两行能放下的话就用第一种
    feiyuanqiu
        22
    feiyuanqiu  
       2018-07-03 10:23:07 +08:00   1
    @jjzhanhun return xxx ? false : true;

    xxx 的运算结果本来就是个 bool,为什么还要用三目运算符再处理一次?
    akira
        23
    akira  
       2018-07-03 11:01:02 +08:00
    前面的 嵌套越少越好
    ConradG
        24
    ConradG  
       2018-07-03 11:51:38 +08:00
    分支多,或分支条件琐碎的,多用第一种。
    分支少,尤其二择多用第二种。
    cuzfinal
        25
    cuzfinal  
       2018-07-03 12:05:25 +08:00
    第一种避免箭头形代码。
    newtype0092
        26
    newtype0092  
       2018-07-03 12:17:37 +08:00
    第二种逻辑更完整,不过可读性差,需要配合 ide 检查,个人觉得这种更适合自动生成而不是手动去写。
    手写代码还是用第一种更合理,逻辑更清楚,而且一定程度上能反应写代码的思路。

    有些人觉得第二种写法这样的冗余工作有助于减少出错,但我认为如果手写这种代码的话眼花出错的概率更高,而且看的头大干扰了自己的思路更容易写错。

    人的思考还是应该求巧,求全是靠各种重复冗余来保证,这是机器该做的,与其不辞辛劳去做冗余工作,不如造一个机器帮自己偷懒。
    agagega
        27
    agagega  
    OP
       2018-07-03 13:50:02 +08:00
    @VVVVVEX 其实一般的新一点的项目我觉得 108 或者 120 字符都可以接受,风格统一的问题。
    agagega
        28
    agagega  
    OP
       2018-07-03 13:51:23 +08:00
    @liuxey
    @crayygy
    确实,这里只是举个例子,还是都带花括号的好
    AltairT
        29
    AltairT  
       2018-07-03 15:46:06 +08:00 via iPhone
    王垠的文章我看过,貌似不是你第二种那样。他明明说了类似意思的话 1 避免箭头代码的方法是将条件反转,提前返回(就是你说的防御代码);2 为了防止遗漏情况,有 if 就必须有 else。
    这两条也不矛盾啊。还是你没理解清楚
    pynix
        30
    pynix  
       2018-07-03 16:41:25 +08:00
    前期可能会先走逻辑(约定参数都有效),,,,后期会慢慢加参数验证。。。
    morethansean
        31
    morethansean  
       2018-07-03 16:51:07 +08:00
    第一种,当年写 WE 养成的习惯 2333333
    luozic
        32
    luozic  
       2018-07-04 10:09:18 +08:00
    直接 if,如果分支切分覆盖不对,还不是一样坑。
    关于     帮助文档     自助推广系统     博客     API     FAQ     Solana     2316 人在线   最高记录 6679       Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 39ms UTC 15:59 PVG 23:59 LAX 07:59 JFK 10:59
    Do have faith in what you're doing.
    ubao msn snddm index pchome yahoo rakuten mypaper meadowduck bidyahoo youbao zxmzxm asda bnvcg cvbfg dfscv mmhjk xxddc yybgb zznbn ccubao uaitu acv GXCV ET GDG YH FG BCVB FJFH CBRE CBC GDG ET54 WRWR RWER WREW WRWER RWER SDG EW SF DSFSF fbbs ubao fhd dfg ewr dg df ewwr ewwr et ruyut utut dfg fgd gdfgt etg dfgt dfgd ert4 gd fgg wr 235 wer3 we vsdf sdf gdf ert xcv sdf rwer hfd dfg cvb rwf afb dfh jgh bmn lgh rty gfds cxv xcv xcs vdas fdf fgd cv sdf tert sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf shasha9178 shasha9178 shasha9178 shasha9178 shasha9178 liflif2 liflif2 liflif2 liflif2 liflif2 liblib3 liblib3 liblib3 liblib3 liblib3 zhazha444 zhazha444 zhazha444 zhazha444 zhazha444 dende5 dende denden denden2 denden21 fenfen9 fenf619 fen619 fenfe9 fe619 sdf sdf sdf sdf sdf zhazh90 zhazh0 zhaa50 zha90 zh590 zho zhoz zhozh zhozho zhozho2 lislis lls95 lili95 lils5 liss9 sdf0ty987 sdft876 sdft9876 sdf09876 sd0t9876 sdf0ty98 sdf0976 sdf0ty986 sdf0ty96 sdf0t76 sdf0876 df0ty98 sf0t876 sd0ty76 sdy76 sdf76 sdf0t76 sdf0ty9 sdf0ty98 sdf0ty987 sdf0ty98 sdf6676 sdf876 sd876 sd876 sdf6 sdf6 sdf9876 sdf0t sdf06 sdf0ty9776 sdf0ty9776 sdf0ty76 sdf8876 sdf0t sd6 sdf06 s688876 sd688 sdf86