ПОЧЕМУ я здесь виноват?нужна помощь.Хотите поместить целое число в массив указателей на символы - PullRequest
2 голосов
/ 18 ноября 2010
#include <stdio.h>

#include <stdlib.h>
int main()
{
    int num = 1;
    char* test[8];
    sprintf(test[0],"%d",num);
    printf("%s\n",test[0]);

}

Ответы [ 5 ]

9 голосов
/ 18 ноября 2010

char *test[8] - это массив из 8 char *, или указатели на строки, и, поскольку вы не укажете, они все установлены в мусорные значения.Таким образом, sprintf пытается записать данные в who-знает-где.

Вместо этого следует использовать char test[8], который выделяет массив из 8 char, а затем sprintf(test, "%d", num);.

ОБНОВЛЕНИЕ: Если вы хотите использовать char * указатели, вы должны выделить место:

char *test = malloc(8 /* see note below */);
sprintf(test, "%d", num);

Если вы хотите использовать массив char * указателей, он работает так же:

char *test[8]; // 8 pointers to strings
test[0] = malloc(8); // allocate memory for the first pointer
sprintf(test[0], "%d", num);

Имейте в виду, что вам придется вызывать malloc для каждого из test[0] - test[7] в отдельности.

Кроме того, как указано в комментариях, если ваш компилятор поддерживает его, вы должны использоватьsnprintf().Это как sprintf, но он принимает дополнительный параметр размером с буфер:

snprintf(test, 8, "%d", num);

и гарантирует, что не будет использовать больше места, чем вы позволите.Это безопаснее, и, если вам нужно, snprintf возвращает количество места, которое он фактически хотел, поэтому, если вы предоставили ему слишком мало места, вы можете realloc и попробовать еще раз.

Примечание: некоторые скажут этодолжно быть malloc(8 * sizeof(char)) (или sizeof *test).Они не правы (по моему объективно правильному мнению; обратите внимание на сарказм)!sizeof(char) гарантированно равно 1, поэтому это умножение не является необходимым.

Некоторые рекомендуют использовать TYPE *p = malloc(x * sizeof *p), так что если TYPE изменится, вам нужно будет изменить его только в одном месте, и sizeof *p адаптируется.Я один из этих людей, но, по моему мнению, вам редко понадобится обновить char * до другого типа.Так как многие функции используют char * и их нужно будет изменить при таком обновлении, я не беспокоюсь о том, чтобы сделать malloc строки более гибкими.

3 голосов
/ 18 ноября 2010

sprintf() не выделяет место для строки; ты должен сделать это сам заранее.

2 голосов
/ 18 ноября 2010

Посмотрите на ваши предупреждения:

test.c: In function ‘main’:
test.c:8: warning: ‘test[0]’ is used uninitialized in this function

Вы выделяете массив из 8 указателей, но используете его без инициализации.Вы должны вызвать malloc и сохранить результат в test[0], прежде чем сможете записать в память, указанную test[0].Вы free в конце.

Полезная функция, присутствующая в GNU и BSD, - это asprintf, которая будет вызывать malloc, чтобы выделить достаточно памяти для форматированной строки:

#include <stdio.h>
#include <stdlib.h>

int main(void) {
    int num = 1;
    char* test[8];
    asprintf(&test[0],"%d",num);
    printf("%s\n",test[0]);
    free(test[0]);
    return 0;
}

(Обратите внимание, что вы передаете адрес вашего указателя на asprintf - так как ваш указатель test[0], его адрес &test[0].)

0 голосов
/ 18 ноября 2010
int main()
{
       char *str[5];
       sprintf(str[0], "%d",55);
       printf("%s\n",str[0]);
       return 0;
}

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

0 голосов
/ 18 ноября 2010

Вы распределили пространство, но вы пропускаете не то. Попробуйте это:

#include <stdio.h>

#include <stdlib.h>
int main()
{
    int num = 1;
    char test[8];
    sprintf(test,"%d",num);
    printf("%s\n",test);

}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...