Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Reason to reverse operands in array access/subscripting

Tags:

arrays

c

In C it is possible to reverse the operands of array subscripting and still achieve the same result. For example a[b] == b[a]. This is because (according to C11 draft N1570, §6.5.2.1/2) a[b] is identical to (*((a)+(b))), and + is commutative. For more, see this question.

Is there ever a scenario (in C, where there's no operator overloading) where swapping the operands of the [] operator doesn't result in the same value at runtime? So, does there exist an a and b for which a[b] != b[a]? (assuming the program compiles and a[b] == a[b])

like image 744
user12341234 Avatar asked Feb 18 '17 19:02

user12341234


People also ask

What is the use of subscript operator in string?

The subscript operator excludes the element that the ending index represents. You can use an expression for the index that returns an integer value. If the expression returns a negative value, the index is considered to be 0.

What is an array subscript?

Array subscripts are a means of displaying or defining the value of a particular element in an array.

What is an array subscript in C++?

The Subscript or Array Index Operator is denoted by '[]'. This operator is generally used with arrays to retrieve and manipulate the array elements. This is a binary or n-ary operator and is represented in two parts: postfix/primary expression.

What is 5 A in array?

a is a pointer to the first element of the array. a[5] is the value that's 5 elements further from a , which is the same as *(a + 5) , and from elementary school math we know those are equal (addition is commutative).


2 Answers

You seem mostly to have answered your own question with your reiteration of why a[b] means the same thing as b[a]. That explanation is correct and founded directly on the standard. The main caveat is that a and b must have types and values such that evaluating a[b] has defined behavior at all. As long as that is the case, the two expressions must evaluate to the same thing. Otherwise, C has nothing to say about whether the two expressions evaluate to the same thing.

On a slightly different tack, if a and b are permitted to represent expressions more complicated than variable names and constants, then it is possible to choose them such that evaluating the overall conditional expression (a)[b] == (b)[a] has undefined behavior, even though evaluating the left-hand and right-hand subexpressions individually has defined behavior. For example,

char array[2] = "a";
int index = 0;
// undefined:
_Bool condition = array[index++] == (index++)[array];

Overall, however, there is no case in which C defines the expression (a)[b] != (b)[a] to be true, regardless of the type, form, or values of a and b.

like image 77
John Bollinger Avatar answered Nov 15 '22 23:11

John Bollinger


Well, if you count this as a valid counterexample:

int *i;
*i[i]; // does not compile
i[*i]; // does compile

The reason is that the subscript operator has higher precedence than the indirection operator, so *i[i] is equivalent to *(i[i]), which is invalid because the subscript operator cannot take two pointer types.


Note that those examples yield undefined behavior when actually executed, of course. It's only supposed to answer the OP's question.

like image 26
cadaniluk Avatar answered Nov 16 '22 00:11

cadaniluk