Каков тип размера std::array, и если размер больше, чем доступно в стеке, генерирует ли он исключение?

Я использую MSVC++.

Если я определяю std::array с размером больше, чем 2^31 - 1, я получаю эту ошибку:

C2148 общий размер массива не должен превышать 0x7fffffff байт

Это заставляет меня сделать вывод, что типом размера является 32-битное целое число со знаком. Но зачем использовать целое число со знаком для размера? поскольку нет отрицательного размера, не было бы лучше, если бы размер мог доходить до 0xffffffff?

Вот интересная вещь, которая происходит со мной:

Если я объявляю массив std::array размером 10000000024, я получаю указанную выше ошибку. Но если я позволю размеру быть 10000000024 * 64, программа скомпилируется без каких-либо проблем.

Это вызывает у меня два вопроса:

1 - почему это происходит?

2 - Я не думаю, что стек настолько велик, чтобы вместить массив такого размера. Выделяется ли массив в куче, например, если он большой? а если нет, что произойдет, если размер массива превысит размер стека? это исключение?


person StackExchange123    schedule 30.03.2020    source источник
comment
10000000024 * 64 переполняет 32-битное целое число и переходит к 49874432, что намного меньше 10000000024.   -  person Igor Tandetnik    schedule 30.03.2020
comment
Тип явно std::size_t (обычно unsigned long), но реализации имеют ограничения на фактическая длина массива, который вы можете определить.   -  person Ken Y-N    schedule 30.03.2020
comment
что произойдет, если размер массива превысит размер стека: то же самое, что произойдет, если вы в противном случае превысите предел стека: возможно, ошибка сегментации во время выполнения.   -  person walnut    schedule 30.03.2020
comment
@RetiredNinja Это не отвечает на все вопросы, только на первую часть.   -  person StackExchange123    schedule 30.03.2020


Ответы (1)


Каков тип размера std::array

Это std::size_t, который является определяемым реализацией беззнаковым целочисленным типом, который достаточно велик, чтобы содержать размер любого объекта в байтах.

1 - почему это происходит?

Согласно сообщению, это происходит потому, что "общий размер массива не должен превышать 0x7ffffffff байт". Похоже, это ограничение конкретной языковой реализации.

Что бы это ни стоило, стандарт C++ предлагает 0x40000 в качестве ориентировочной рекомендации для минимального предела максимального размера объекта. 0x7ffffffff значительно превосходит эту рекомендацию. В системе Linux x86-64 максимальный размер объекта равен 0x7ffffffffffffffff.

Выделяется ли массив в куче, например, если он большой?

Где выделяется память для объекта, зависит от типа используемого хранилища и от реализации языка. Размер объекта обычно не влияет на это. std::array никогда не выделяет динамическую память.

что произойдет, если размер массива превысит размер стека?

Неважно, насколько превышен размер стека выполнения. Язык не определяет, что происходит, и не признает существование «стека». Это конкретная концепция реализации. Таким образом, то, что происходит, зависит от реализации. Если повезет, программа вылетает. Если вам не повезет, ваши секреты попадут к хакерам.

person eerorika    schedule 30.03.2020