Строки инициализации в C - PullRequest
1 голос
/ 21 июля 2010

У меня вопрос о том, как правильно манипулировать инициализацией строк c Например, следующий код не всегда корректен.

char *something;
something = "zzzzzzzzzzzzzzzzzz";

Я тестирую небольшое увеличение числа Зетов, и, фактически, сбой программы примерно в две строки, так каков реальный предел размера в этом массиве символов? Как я могу быть уверен, что это не приведет к сбою, зависит ли реализация этого лимита? Является ли следующий код правильным подходом, который я всегда должен использовать?

char something[FIXEDSIZE];
strcpy(something, "zzzzzzzzzzzzzzzzzzz");

Ответы [ 4 ]

8 голосов
/ 21 июля 2010

Как вы говорите, манипулирование этой строкой приводит к неопределенному поведению:

char *something;
something = "zzzzzzzzzzzzzzzzzz";

Если вам интересно, почему, см. «C Строковые литералы: куда они идут?» .

Если вы планируете манипулировать вашей строкой вообще (т.е. если вы хотите, чтобы она была изменчивой), вы должны использовать это:

char something[] = "skjdghskfjhgfsj";

В противном случае просто объявите ваш char * как const char *, чтобы указать, что он указывает на константу.

Во втором примере компилятор будет достаточно умен, чтобы объявить это как массив в стеке точного размера для хранения строки. Таким образом, размер этого ограничен вашим стеком.

Конечно, вы, вероятно, все равно захотите указать размер, так как это обычно полезно знать при работе со строкой.

1 голос
/ 21 июля 2010

Первый пример неверен только в том, что char *something действительно должно быть const char *something. В противном случае это:

const char *something = "fooooooooooooooooooooooobar";

... должно работать и не падать.

char something[FIXEDSIZE];

... однако, этот тип обычно может завершиться с переполнением стека, если вы переполните стек, что зависит от того, насколько велик этот стек, насколько велик этот массив, где вызывается и т. Д. 1009 *

1 голос
/ 21 июля 2010

Второе всегда правильно.

Первое верно только в том случае, если вы никогда не меняете строку, поскольку вы назначили указатель на фиксированные данные.

0 голосов
/ 21 июля 2010

сначала никогда не должен падать. second завершится сбоем, как только число 'z' + 1 превысит доступное пространство на странице стека или если вы попытаетесь вернуться из функции.

...