Вам нужно отбросить const для инициализации полей структуры malloc:
struct deneme *mydeneme = malloc(sizeof(struct deneme));
*(int *)&mydeneme->a = 15;
*(int *)&mydeneme->b = 20;
В качестве альтернативы, вы можете создать инициализированную версию структуры и запомнить ее:
struct deneme deneme_init = { 15, 20 };
struct deneme *mydeneme = malloc(sizeof(struct deneme));
memcpy(mydeneme, &deneme_init, sizeof(struct deneme));
Вы можете сделать deneme_init статическим и / или глобальным, если вы делаете это много (поэтому его нужно создать только один раз).
Объяснение того, почему этот код не является неопределенным поведением, как это предлагаетсясогласно некоторым комментариям, используя стандартные ссылки C11:
Этот код не нарушает 6.7.3 / 6, поскольку пространство, возвращаемое malloc
, не является "определенным объектом с константным типом ".Выражение mydeneme->a
это не объект, это выражение.Несмотря на то, что он имеет const
-квалифицированный тип, он обозначает объект, который не был определен с помощью типа с константой (фактически, вообще не определен ни с одним типом).
правило строгого алиасинга никогда не нарушается записью в пространство, выделенное malloc
, потому что эффективный тип (6.5 / 6) обновляется при каждой записи.
(Строгое правило алиасинга может быть нарушено чтением из пространства, выделенного на malloc
.)
В примерах кода Криса первый устанавливает эффективный тип целочисленных значений равным int
, а второйустанавливает эффективный тип на const int
, однако в обоих случаях чтение этих значений с помощью *mydeneme
является правильным, поскольку правило строгого псевдонима (п. 6,5 / 7, 2) позволяет читать объект через выражение, равное или большееуточняется, чем эффективный тип объекта.Поскольку выражение mydeneme->a
имеет тип const int
, его можно использовать для чтения объектов эффективного типа int
и const int
.
.