Search code examples
cdeclarationcomma-operator

Nuances of comma seperator and comma operator when used in initialization and declaration statements


I was playing around with the , operator after reading several of the answers on a Stack Overflow post (What does the comma operator , do?). Further, I was playing around with the , separator after reading this post: comma operator and comma seperator in c++. Consider the following two code snippets:

Code 1

#include<stdio.h>
int main(void) 
{
  int a, b;      /* comma functions as a separator */
  a = 5, b=9;    /* NOT SURE how comma functions */
  printf("a = %d \n",a) , printf("b = %d \n",b);     /* comma functions as an operator */      
}

Code 2

#include<stdio.h>
int main(void) 
{
  int a, int b;   /* not allowed - compiler error ... NOT SURE how comma functions */
  a = 5, b=9;     /*NOT SURE how comma functions */
  printf("a = %d \n",a) , printf("b = %d \n",b);      /*comma functions as an operator */      
}

The top code (Code 1) is fine...and prints out a=5 and b=9; however, the bottom code (Code 2) does not make it past the compiler and cites the int a, int b ; line as the incriminating action.


There are a lot of questions bundled up in these two code snippets but I'll bullet out the ones I care about the most:

  1. In the statement a=5,b=9; is that , functioning as a separator or an operator? I've read that in initialization statements, commas function as separators. However, given my understanding of what a comma operator would do, I feel like classifying this comma as an operator makes sense as well.

  2. Why is int a, int b not allowed? If the comma was allowed to behave as an operator, then certainly this would make sense, right? int a would be evaluated first and it would have the side effect of labeling some place in memory with the identifier of a and then int b would be processed in a similar way. Therefore, it seems as though the compiler does not want to alter the interpretation of the , in this case (i.e. it only ever wants to think of it as a separator).

An explanation would be greatly appreciated! Thanks~


Solution

  • The declaration in C is defined (in particularly) like

    declaration:
        declaration-specifiers init-declarator-list ; 
    

    where the term init-declarator-list is defined like

    init-declarator-list:
        init-declarator
        init-declarator-list , init-declarator
    

    So in the first program in this declaration

    int a, b;
    

    there is no comma operator. The comma is used to separate init-declarators in the init-declarator-list.

    This statement

    a = 5, b=9; 
    

    is indeed a statement with the comma operator expression.

    This statement

    printf("a = %d \n",a) , printf("b = %d \n",b);
    

    is also a statement with the comma operator expression.

    This declaration in the second program is incorrect

    int a, int b; 
    

    because the declaration specifier int is used inside the init-declarator-list.

    As for the comma operator then according to the C Standard (6.5.17 Comma operator)

    2 The left operand of a comma operator is evaluated as a void expression; there is a sequence point between its evaluation and that of the right operand. Then the right operand is evaluated; the result has its type and value

    You can use the comma operator as an initializer of a variable for example like

    int a = 10, b = 20;
    int c = ( a++, b++, a + b );
    

    The variable c will be initialized by the value 32.

    Here is a demonstrative program.

    #include <stdio.h>
    
    int main(void) 
    {
        int a = 10, b = 20;
        
        printf( "a = %d, b = %d\n", a, b );
        
        int c = ( a++, b++, a + b );
    
        printf( "a = %d, b = %d, c = %d\n", a, b, c );
    
        return 0;
    }
    

    Its output is

    a = 10, b = 20
    a = 11, b = 21, c = 32