Я читаю параграф 7 из 6.5 в ISO/IEC 9899: TC2.
Он допускает доступ к объекту lvalue через:
совокупность или тип объединения, который включает один из вышеупомянутых типы среди своих членов (в том числе, рекурсивно, член subaggregate или contains union),
Пожалуйста, обратитесь к документу за тем, какие "вышеупомянутые" типы, но они, безусловно, включают эффективный тип объекта.
В разделе, отмеченном как
Цель этого списка - указать те обстоятельства, при которых объект может быть или не быть псевдонимом.
Я прочел это, сказав (например) следующее:
#include <stdlib.h>
#include <stdio.h>
typedef struct {
unsigned int x;
} s;
int main(void){
unsigned int array[3] = {73,74,75};
s* sp=(s*)&array;
sp->x=80;
printf("%d\n",array[0]);
return EXIT_SUCCESS;
}
Эта программа должна вывести 80.
Я не выступаю за это как хорошую (или очень полезную) идею и признаю, что я частично ее интерпретирую, потому что я не могу думать, что еще это значит и не может поверить в бессмысленное предложение!
Тем не менее, я не могу видеть очень вескую причину, чтобы запретить это. Мы знаем, что выравнивание и содержимое памяти в этом месте совместимы с sp->x
, так почему бы и нет?
Похоже, что если я добавлю (скажем) a double y;
к концу структуры, я все равно могу получить доступ к array[0]
через sp->x
таким образом.
Однако даже если массив больше, чем sizeof(s)
, любая попытка доступа к sp->y
- это поведение "все ставки выключено" undefined.
Могу ли я вежливо просить людей сказать, что это предложение оправдывает, а не идти в плоский спин, выкрикивая "строгий псевдоним UB строгое сглаживание UB", похоже, слишком часто является способом этих вещей.