Массив в C-структуре
Я хочу иметь два массива в структуре, которые инициализируются при запуске, но нуждаются в дальнейшем редактировании. Мне нужно три экземпляра структуры, чтобы я мог индексировать в определенную структуру и изменять, как я желаю. Возможно ли это?
Это то, что я думал, что могу сделать, но я получаю ошибки:
struct potNumber{
int array[20] = {[0 ... 19] = 10};
char *theName[] = {"Half-and-Half", "Almond", "Rasberry", "Vanilla", …};
} aPot[3];
Затем я обращаюсь к структурам следующим образом:
printf("some statement %s", aPot[0].array[0]);
aPot[0].theName[3];
…
Ответы
Ответ 1
У самих структур нет данных. Вам нужно создать объекты типа struct и установить объекты...
struct potNumber {
int array[20];
char *theName[42];
};
/* I like to separate the type definition from the object creation */
struct potNumber aPot[3];
/* with a C99 compiler you can use 'designated initializers' */
struct potNumber bPot = {{[7] = 7, [3] = -12}, {[4] = "four", [6] = "six"}};
for (i = 0; i < 20; i++) {
aPot[0].array[i] = i;
}
aPot[0].theName[0] = "Half-and-Half";
aPot[0].theName[1] = "Almond";
aPot[0].theName[2] = "Rasberry";
aPot[0].theName[3] = "Vanilla";
/* ... */
for (i = 0; i < 20; i++) {
aPot[2].array[i] = 42 + i;
}
aPot[2].theName[0] = "Half-and-Half";
aPot[2].theName[1] = "Almond";
aPot[2].theName[2] = "Rasberry";
aPot[2].theName[3] = "Vanilla";
/* ... */
Ответ 2
В массиве C struct элементы должны иметь фиксированный размер, поэтому char *theNames[]
недействителен. Также вы не можете инициализировать структуру таким образом. В массивах C статичны, т.е. Динамически не изменять их размер.
Правильное объявление структуры будет выглядеть следующим образом:
struct potNumber{
int array[20];
char theName[10][20];
};
и вы инициализируете его следующим образом:
struct potNumber aPot[3]=
{
/* 0 */
{
{10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10 /* up to 20 integer values*/ },
{"Half-and-Half", "Almond", "Raspberry", "Vanilla", /* up to 10 strings of max. 20 characters */ }
},
/* 1 */
{
{10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10 /* up to 20 integer values*/ },
{"Half-and-Half", "Almond", "Raspberry", "Vanilla", /* up to 10 strings of max. 20 characters */ }
},
/* 2 */
{
{10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10 /* up to 20 integer values*/ },
{"Half-and-Half", "Almond", "Raspberry", "Vanilla", /* up to 10 strings of max. 20 characters */ }
}
};
Но я уверен, что это не то, что вы хотите. Разумный способ сделать это требует некоторого кода шаблона:
struct IntArray
{
size_t elements;
int *data;
};
struct String
{
size_t length;
char *data;
};
struct StringArray
{
size_t elements;
struct String *data;
};
/* functions for convenient allocation, element access and copying of Arrays and Strings */
struct potNumber
{
struct IntArray array;
struct StringArray theNames;
};
Лично я настоятельно рекомендую не использовать голые C-массивы. Выполнение всего с помощью вспомогательных структур и функций позволяет вам избавиться от буфера под /overruns и других проблем. Каждый серьезный C-кодер строит библиотеку поддеробных кодов с такими вещами со временем.