Скажем, у меня есть следующая структура.

struct Vector3{
    double Values[3];
};

Я знаю, что могу сделать что-то вроде:

struct Vector3 v1;
v1.Values[0] = -1;
printf("%f", vi.Values[0]);

И это будет работать нормально. Мне не нужно было выделять / вызывать .Values. Компиляция с -c99 -Wall не дает мне никаких предупреждений. Но у меня есть вопросы по поводу такой структуры.

В этом случае, где v1 - локальная переменная:

  • "Двойники" .Values ​​размещаются в стеке или куче?
  • Если они размещены в куче, гарантированно ли этот код будет работать всегда? Или это зависит от компилятора?

Если есть эта другая структура

struct Triplet{
    double First;
    double Second;
    double Third;
};

Могу ли я «запомнить» содержимое Vector3 в Triplet?

И последнее, но не менее важное: что насчет этой структуры? Те же правила, что и у Vector3?

struct Matrix3{
    double Values[3][3];
};
2
Trauer 27 Окт 2015 в 21:36

2 ответа

Лучший ответ

Где расположены массивы в структурах

То же место, где выделяется сама структура, либо в стеке, либо в куче, в зависимости от того, как вы создаете экземпляр структуры.

struct Vector3 v1;

Выделяет всю память, необходимую для Vector3 в стеке.

Могу ли я «запомнить» содержимое Vector3 в Triplet?

Это зависит от того, как структура упакована на вашей целевой платформе, и от настроек вашего компилятора и, возможно, от #pragma, влияющего на упаковку. Нет общей гарантии, что вы можете просто скопировать данные. Он будет работать на некоторых платформах, а затем может дать сбой на других платформах.

4
Eric J. 27 Окт 2015 в 18:42

Структура выделяется целиком, включая массивы.

struct Vector3 v1;

Здесь полное содержимое структуры (массив из трех двойников) размещается в стеке, если это локальное объявление (внутри функции), в другом месте в области статических данных. Никогда не в куче.

Могу ли я «запомнить» содержимое Vector3 в Triplet?

Это, вероятно, могло бы сработать, но это было бы опасно, потому что расположение полей структуры внутри структуры зависит от компилятора, Triplet может иметь отступы между двойниками. В общем, вы не должны memcpy разных структур.

Что касается последнего примера (двухмерный массив внутри структуры), да, он такой же, как и предыдущий, девять значений размещаются внутри структуры.

2
leonbloy 27 Окт 2015 в 18:52