V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
bwangel
V2EX  ›  C

C 语言的语法问题

  •  
  •   bwangel · 2015-05-27 20:52:10 +08:00 · 1175 次点击
    这是一个创建于 3262 天前的主题,其中的信息可能已经有所发展或是发生改变。
    #include <stdio.h>
    int main(int argc,char *argv[])
    {
        int num;
    
        printf("%d %d\n",(num=100,1),num);
    
        return 0;
    }
    

    上面是代码,谁能给我解释一下那个(num=100,1)的值为什么是1,这条语句是个啥意思啊?

    20 条回复    2015-08-17 10:34:56 +08:00
    bwangel
        1
    bwangel  
    OP
       2015-05-27 20:53:03 +08:00
    程序的运行结果是
    1 100
    bwangel
        2
    bwangel  
    OP
       2015-05-27 20:53:41 +08:00
    感觉这个语句好神奇啊,哪位大牛能给俺科普科普,不胜感激!
    moro
        3
    moro  
       2015-05-27 20:55:32 +08:00
    逗号表达式的返回值,应该是最后一个逗号的值。
    wy315700
        4
    wy315700  
       2015-05-27 20:55:51 +08:00
    @bwangel
    num=100,1
    这句话首先 是给num赋值100
    其次,这个是逗号分割的表达式, (a,b,c,d) 这个表达式的值 是d,
    所以 (num=100,1) = 1
    moro
        5
    moro  
       2015-05-27 20:55:54 +08:00
    其它语言也是一样的。
    rrfeng
        6
    rrfeng  
       2015-05-27 20:56:53 +08:00   ❤️ 1
    (num=100,1)

    逗号运算符的优先级最低,作为一个整体,逗号表达式的值为最后一个表达式的值。
    xdeng
        7
    xdeng  
       2015-05-27 20:57:10 +08:00
    3、4楼正解
    bwangel
        8
    bwangel  
    OP
       2015-05-27 21:06:06 +08:00
    可不可以这样想,逗号的功能就是分割语句,相当与将多个语句整合成一条。然后它的结合性是从左到右。比如这条语句:

    ```c
    num = 10, num = 20, num = 30
    ```

    先执行num = 30 ,再执行num=20,最后执行num = 10

    然后相当于变成了这个样子的代码(仅供参考,可能不是很严谨)
    ```c
    10,20,30
    ```

    然后再执行10,20,代码就变成了这个样子
    ```c
    20,30
    ```

    最后执行20,30这条语句,然后整个表达式的值就是30了?

    各位看官,我分析的对不?
    bwangel
        9
    bwangel  
    OP
       2015-05-27 21:06:36 +08:00
    额,为啥回复就不支持markdown。。。。。
    theFool
        10
    theFool  
       2015-05-27 21:22:14 +08:00
    @bwangel 不对。 num应该是==30. 照你的说法num==10了。
    msg7086
        11
    msg7086  
       2015-05-27 21:25:25 +08:00
    并非是分割语句,而是分割表达式。

    a = b 是赋值表达式
    a = b; 是赋值语句
    wy315700
        12
    wy315700  
       2015-05-27 21:27:39 +08:00
    @bwangel
    逗号表达式是C的一种表达式

    http://en.wikipedia.org/wiki/Comma_operator
    bwangel
        13
    bwangel  
    OP
       2015-05-27 21:37:01 +08:00
    @msg7086 ,恩,确实是,我的表达有误!
    bwangel
        14
    bwangel  
    OP
       2015-05-27 21:40:11 +08:00
    @theFool ,不是很理解你想说的意思,意思是我分析的那个num赋值顺序(30,20,10)不对,还是说我那个=不对,应该写成==
    theFool
        15
    theFool  
       2015-05-27 21:43:15 +08:00
    @bwangel 分析不对。照你的说法先执行num = 30 ,再执行num=20,最后执行num = 10 ,那num最后应该是等于10的。
    qiuyi116
        16
    qiuyi116  
       2015-05-27 22:49:29 +08:00
    (num=100, 1)整体是一个逗号表达式,它的值是最后一个逗号后的值,即1;而逗号表达式的前面一个表达式是个赋值表达式,使得num的值为100。所以输出的值为1,100.
    Maxi
        17
    Maxi  
       2015-05-30 21:54:58 +08:00
    优先级问题 ,逗号运算符级别最低 。所以先 100先给赋值用, 再计算逗号表达式的值. 如果num = (100, 1) 则是先计算逗号表达式的值。
    FrankHB
        18
    FrankHB  
       2015-06-06 14:35:52 +08:00
    @bwangel 逗号的功能不一定是“分隔语句”。
    首先你得了解,C的语法中逗号并不都是一回事。有些逗号只是标点而不是操作符,如函数调用的postfix-expreesion中的分隔参数的逗号;而逗号表达式里的逗号操作符是另一回事。
    最重要的影响语义的差异之一是,前者不限定求值顺序,而后者会插入一个sequence point。这里没有这个坑,但不知道迟早被坑。
    语句之间是有sequence point的。从这个意义上来看,逗号操作符可以认为是在“分隔语句”。虽然实际上更像是个应付语句可用性缺陷设计的workaround(嘛,while条件里塞不进语句咋办……用逗号擦屁股吧)。而其它逗号,就显然不是这个意思。
    printf("%d %d\n",(num=100,1),num);这坨里面,本来分号之前按postfix-expression来看,里面的逗号是argument-expression-list的组成部分——用于分隔作为参数assignment-expression的硬编码的分隔符而不是逗号操作符,但这里硬加了个括号,而作为argument的assignment-expression当然没法包括没配对的括号,语法分析就只能把(num=100,1)当作整个assignment-expression,然后继续规约:conditional-expression→...→primary-expression→( expression )→expression , assignment-expression——这里面的逗号就是逗号操作符了。
    这里的要点是语法规则决定了assignment-expression的逗号不会被作为操作符,而加上括号以后括号里面的东西可以不是assignment-expression而是允许包含逗号操作符的一般expression,因此加上括号以后含义就变了。
    wlee1991
        19
    wlee1991  
       2015-08-17 09:26:25 +08:00 via iPhone
    @FrankHB 有没有英文出处 可以贴出来吗
    wlee1991
        20
    wlee1991  
       2015-08-17 10:34:56 +08:00
    c 语言提供一种特殊的运算符,逗号运算符,优先级别最低,它将两式联接起来,如:( 3+5,6+8 )称为逗号表达式,其求解过程先表达式 1 ,后表达式 2 ,整个表达式值是表达式 2 的值。
    如:(3+5, 6+8 )的值是 14 ,(a=3*5, a*4 )的值是 60 ,原因在于赋值运算符优先级高于逗号运算符。
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   我们的愿景   ·   实用小工具   ·   2255 人在线   最高记录 6543   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 28ms · UTC 05:52 · PVG 13:52 · LAX 22:52 · JFK 01:52
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.