8

In C, array subscription: a[b] is merely the syntactic sugar equivalent of dereferencing after pointer arithmetic: *(a+b) (as explained, say, here).

How is array subscription interpreted in C++, for base types? (Not for classes, for which we have overload semantics)? And, more specifically, what type does C++ expect to appear as the subscript? Is it a ptrdiff_t?

3
  • 1
    C++ does the same thing C does for base types. Commented Dec 4, 2013 at 14:53
  • I think the article you link to explains it well. For basic types, a[b] is valid if and only if *(a + b) is. So the valid types for b depend on the type of a, but basically any integer type is fine if a is a pointer-to-object type, or any pointer-to-object type if a is an integer type. What's the question, are you just asking for confirmation that answer is correct when it says, "C++ inherited this definition from C"? Commented Dec 4, 2013 at 14:54
  • I think it does the same thing for all data types...I can't think of a data type treated differently by c++ Commented Dec 4, 2013 at 14:54

2 Answers 2

8

How is array subscription interpreted in C++,

In C++ E1[E2] is identical to *((E1)+(E2))

what type does C++ expect to appear as the subscript?

C++ expects a unscoped enumeration or integral type both items are covered in the draft C++ standard section 5.2.1 Subscripting paragraph 1 which says (emphasis mine):

A postfix expression followed by an expression in square brackets is a postfix expression. One of the expressions shall have the type “pointer to T” and the other shall have unscoped enumeration or integral type. The result is an lvalue of type “T.” The type “T” shall be a completely-defined object type.62 The expression E1[E2] is identical (by definition) to *((E1)+(E2)) [ Note: see 5.3 and 5.7 for details of * and + and 8.3.4 for details of arrays. —end note ]

As James points out, the wording One of the expressions shall have allows the pointer and subscript to be interchanged, for example:

#include <iostream>

int main()
{
    int arr[5] = {1, 2, 3, 4, 5 } ;

    std::cout << arr[2] << ":" << 2[arr] << std::endl ;
}

Using the alternative syntax 2[arr] is not recommended, most people won't know what this is doing it makes the code less readable and hence less maintainable.

which is similar to the relevant section in the draft C99 standard 6.5.2.1 Array subscripting paragraph 2 which says(emphasis mine):

A postfix expression followed by an expression in square brackets [] is a subscripted designation of an element of an array object. The definition of the subscript operator [] is that E1[E2] is identical to (*((E1)+(E2))). Because of the conversion rules that apply to the binary + operator, if E1 is an array object (equivalently, a pointer to the initial element of an array object) and E2 is an integer, E1[E2] designates the E2-th element of E1 (counting from zero).

Sign up to request clarification or add additional context in comments.

5 Comments

Note that it is "one of the expressions" which has an integral type. Something like int * array; [10]array is perfectly legal (and perfectly horrible).
@JamesKanze fair point, I should probably note that, it is not really obvious.
@JamesKanze actually you mean 10[array] the grammar does not allow for [10]array.
Yes. (It's not something I use everyday:-)) And since you mention it now, do mention that it is not at all recommended.
@JamesKanze amended and I had to try it out myself as well.
3

C++ is exactly the same as C in this respect. C++11 §5.2.1:

The expression E1[E2] is identical (by definition) to *((E1)+(E2))

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.