инициализация массива структуры с использованием memset - PullRequest
16 голосов
/ 02 августа 2010

gcc 4.4.4 c89

У меня следующая структура.

struct device_sys
{
    char device[STRING_SIZE];
    int id;
    char category;
};

int main(void)
{
    struct device_sys dev_sys[NUM_DEVICES];

    memset(dev_sys, 0, (size_t)NUM_DEVICES * sizeof(dev_sys));

    return 0; 
}

Я получаю дамп стека при вызове memset.Разве это не правильный способ инициализации массива структуры?

Ответы [ 4 ]

32 голосов
/ 02 августа 2010

Или

memset(&dev_sys, 0, sizeof dev_sys);

или

memset(dev_sys, 0, NUM_DEVICES * sizeof(struct device_sys));

Или, если вы предпочитаете

memset(dev_sys, 0, NUM_DEVICES * sizeof *dev_sys);

но не то, что есть в исходном варианте.

Обратите внимание, что в вашем конкретном случае во всех вариантах вы можете использовать либо &dev_sys, либо dev_sys в качестве первого аргумента. Эффект будет таким же. Тем не менее, &dev_sys является более подходящим в первом варианте, так как если следует идиома memset(ptr-to-object, object-size). Во втором и третьем вариантах более целесообразно использовать dev_sys (или &dev_sys[0]), поскольку оно следует идиоме memset(ptr-to-first-element, number-of-elements * element-size).

P.S. Конечно, вместо использования всего этого хакерского memset трюка, в вашем конкретном случае вы должны были просто объявить ваш массив с инициализатором

struct device_sys dev_sys[NUM_DEVICES] = { 0 };

Нет memset необходимо.

9 голосов
/ 02 августа 2010

В вашем коде есть опечатка.Исправление:

memset(dev_sys, 0, (size_t)NUM_DEVICES * sizeof(struct device_sys));

Выбор хороших имен позволяет избежать половины ошибок.Я бы порекомендовал "устройства".

1 голос
/ 02 августа 2010

Для массива sizeof возвращает вам весь размер массива, а не размер отдельного элемента. Оператор sizeof является одним из немногих мест, где массив не рассматривается как указатель на его первый элемент.

1 голос
/ 02 августа 2010

Вы должны передать оператору sizeof тип, а не переменную.

memset(dev_sys, 0, (size_t)NUM_DEVICES * sizeof(struct device_sys));

Я предпочитаю использовать typedef для структуры.

typedef struct tag_device_sys
{
    char device[STRING_SIZE];
    int id;
    char category;
} device_sys;

Вы можете использовать memset следующим образом:

    memset(dev_sys, 0, (size_t)NUM_DEVICES * sizeof(device_sys));
...