Инициализация структуры до 0
Если у меня есть такая структура:
typedef struct
{
unsigned char c1;
unsigned char c2;
} myStruct;
Каким будет самый простой способ инициализировать эту структуру до 0?
Было бы достаточно?
myStruct _m1 = {0};
или мне нужно будет явно инициализировать каждый член до 0?
myStruct _m2 = {0,0};
Ответы
Ответ 1
Первое проще всего (включает в себя меньше ввода текста), и он гарантированно работает, все члены будут установлены в 0
[Ref 1].
Второй - более читаемый.
Выбор зависит от предпочтений пользователя или от того, который соответствует вашему стандарту кодирования.
[Ссылка 1] Ссылка C99 Стандарт 6.7.8.21:
Если в списке, заключенном в скобках, меньше инициализаторов, чем в элементе или элементах совокупности или меньше символов в строковом литерале, используемом для инициализации массива с известным размером, чем в массиве, остальная часть агрегат должен быть инициализирован неявным образом так же, как объекты, имеющие статическую продолжительность хранения.
Хорошее чтение:
C и С++: частичная инициализация автоматической структуры
Ответ 2
Если данные представляют собой статическую или глобальную переменную, она по умолчанию заполняется нулем, поэтому просто объявите ее myStruct _m;
Если данные представляют собой локальную переменную или выделенную кучей зону, очистите ее с помощью memset
как:
memset(&m, 0, sizeof(myStruct));
Текущие компиляторы (например, последние версии gcc
) оптимизируют это на практике. Это работает только в том случае, если все нулевые значения (включая нулевые указатели и ноль с плавающей точкой) представлены как все нулевые биты, что верно для всех платформ, о которых я знаю (но стандарт C разрешает реализации, где это ложь, я не знаю такой реализации).
Возможно, вы можете ввести код myStruct m = {};
(который может быть принят как расширение), но я нахожу это довольно уродливым. И если первый член структуры не является скалярным, т.е. Является объединением, структурой или массивом, тогда некорректное кодирование myStruct m = {0};
.
Я чувствую, что использование memset
для локальных структур является лучшим, и это лучше говорит о том, что во время выполнения необходимо что-то сделать (в то время как обычно глобальные и статические данные можно понимать как инициализированные во время компиляции, без каких-либо затрат во время выполнения).
Ответ 3
См. §6.7.9 Инициализация:
21 Если в списке, заключенном в фигурные скобки, меньше инициализаторов, чем элементов или элементов совокупности или меньше символов в строковом литерале, используемом для инициализации массива известных размера, чем есть элементы в массиве, остальная часть совокупности должна быть инициализируется неявно так же, как и объекты, имеющие статическую продолжительность хранения.
Итак, да, оба они работают. Обратите внимание, что в C99 также может быть использован новый способ инициализации, называемый назначенной инициализацией:
myStruct _m1 = {.c2 = 0, .c1 = 1};