Двойные стандарты компилятора

int a[42]{};
std::cout << a[42];

std::string str(42, 'x');
std::cout << str[42];

Почему в первом случае срабатывает предупреждение о неопределенном поведении, а во втором нет?


Ответы (2 шт):

Автор решения: Roman Konoval

Для string доступ к элементу в позиции с индексом равным длине не ведет к неопределенному поведению.

Вот что говорит стандарт:

21.3.2.5 Element access[string.access]

constexpr const_reference operator[](size_type pos) const;
constexpr reference operator[](size_type pos);

  1. Preconditions: pos <= size().

  2. Returns: *(begin() + pos) if pos < size(). Otherwise, returns a reference to an object of type charT with value charT(), where modifying the object to any value other than charT() leads to undefined behavior.

  3. Throws: Nothing.

В следующем коде имеет место случай 2, а именно pos == size(), а тут поведение определено однозначно:

std::string str(42, 'x');
std::cout << str[42];
→ Ссылка
Автор решения: gbg

Потому что теоретически, у класса string квадратные скобки могут быть переопределены и запускать ракету на Марс.

→ Ссылка