Поведение неинициализированных структур C

#c #struct #initialization

#c #структура #инициализация

Вопрос:

Допустим, мы объявляем массив структур в локальной области видимости:

     int main()
{
    RandomStruct array [1000];
}
 

В настоящее время структуры в массиве неинициализированы. Хотя это означает, что переменные структуры также неинициализированы, означает ли это что-нибудь еще? Например, если я, например, устанавливаю все переменные из неинициализированной структуры в желаемое значение, а затем использую функции этой структуры, или если я использую функции структуры, которые не используют неинициализированные переменные, прежде чем я их установлю. Правильно ли я полагаю, что неинициализированы будут только переменные и что массив просто назначает произвольную память каждой из переменных структуры?

Комментарии:

1. «В настоящее время структуры в массиве неинициализированы». Вызывается конструктор структуры по умолчанию. Содержащие переменные (структуры) неинициализируются, только если конструктор по умолчанию их не инициализирует.

2. Почему не следует вызывать конструктор по умолчанию, если массив является локальным?

3. » Вы ошибаетесь » Тем не менее, я сказал: «Содержащие переменные (структуры) неинициализированы, только если конструктор по умолчанию их не инициализирует.», а конструктор по умолчанию, который генерируется компилятором, их не инициализирует. Пожалуйста, не утверждайте, что люди ошибаются, когда вы не читали все, что они написали.

4. @12123232 это не похоже на правильную характеристику. В обоих случаях используется ctor по умолчанию, и он может быть либо сгенерирован компилятором, либо предоставлен пользователем, в зависимости от того, был ли он объявлен при написании фактического определения структуры

5. @12123232 » таким образом, в случае структур с локальными массивами они создаются с помощью конструктора по умолчанию, сгенерированного компилятором » Не обязательно. Вот почему я написал свой комментарий. Конструктор может быть предоставлен пользователем, который может инициализировать содержащие переменные. Не зная, что RandomStruct это такое, невозможно узнать, будут ли инициализированы его значения-члены или нет. Если это так, например struct RandomStruct {int a; RandomStruct () : a(-1) {}}; , — a будет инициализироваться -1 каждый раз, независимо от того, где выполняется такое построение.

Ответ №1:

В настоящее время структуры в массиве неинициализированы

Нет, они инициализированы по умолчанию.

Хотя это означает, что переменные структуры также неинициализированы

Влияние на элементы зависит от определения RandomStruct . В зависимости от этого определения инициализация по умолчанию RandomStruct может иметь эффект инициализации по умолчанию некоторых или всех нестатических элементов данных RandomStruct . В конечном итоге это может привести к инициализации переменной неклассового типа по умолчанию как члена RandomStruct или члена члена и т. Д. Эта переменная неклассового типа будет иметь неопределенное значение.

Например, если я, например, устанавливаю все переменные из неинициализированной структуры в желаемое значение, а затем использую функции этой структуры, или если я использую функции структуры, которые не используют неинициализированные переменные, прежде чем я их установлю

Если все члены инициализируются определенными значениями перед использованием, все в порядке. Вызовы функций-членов, которые не «соблюдают» неопределенные значения, в порядке.

Правильно ли я полагаю, что неинициализированы будут только переменные и что массив просто назначает произвольную память каждой из переменных структуры?

Это не совсем так. Это означало бы, что наблюдение неопределенных значений в порядке, но их значение просто неизвестно. Это не так. Но пока вы не соблюдаете значения, это верная интуиция.

Можно оставить их неопределенными до тех пор, пока они не будут соблюдены. Но «наблюдать» неопределенное значение, создавая его при любой оценке, за исключением очень ограниченных, перечисленных условий, является неопределенным поведением.

Это означает, что правильной программе не разрешено наблюдать значение, но компилятор также не обязан его диагностировать. Однако компилятор может предположить, что это никогда не выполняется (потому что правильная программа не может этого сделать), а C не предъявляет никаких требований к недопустимой программе.