Skip to content

Trivia impact: none

The Subscript That Runs Backwards

the index and the array, on the wrong sides of the brackets

int scores[] = {10, 20, 30};

std::cout << "scores[2] = " << scores[2] << "\n";
std::cout << "2[scores] = " << 2[scores] << "\n";

Does this compile? What does it print?

Answer
scores[2] = 30
2[scores] = 30

It compiles without a single warning under -Wall -Wextra. Array subscripting is commutative.

Why

The standard defines built-in subscripting by translation, not by magic: [expr.sub] says E1[E2] is identical to *((E1)+(E2)), with one operand a pointer and the other an integral type. The array decays to a pointer, and + on a pointer and an integer is commutative like any other addition — so 2[scores] becomes *(2 + scores), which is the same address *(scores + 2) names. Nothing is being cleverly reinterpreted; the two spellings were never different expressions in the first place. This holds only for the built-in operator: an overloaded operator[] is an ordinary member function, so 2[myVector] does not compile.

Where it shows up

Nowhere you want it to. It is a favourite of obfuscated-code contests and interview trivia, and its one honest use is as evidence that C++ arrays really are pointer arithmetic underneath — which is the same reason sizeof forgets an array's length once it is passed to a function.

Takeaway: a[i] is spelled shorthand for *(a + i), and addition does not care which side you wrote first.

Try it: g++ -std=c++17 main.cpp -o demo && ./demo

Open in Compiler Explorer ↗ Quiz this entry