Строки в стиле c безопасны? - PullRequest
1 голос
/ 11 октября 2009

В c / c ++ некоторые люди используют строки в стиле c, например:

char *str = "This is a c-styled string";

Мой вопрос - это безопасно? Как я вижу, они создали указатель на символ, который указывает на первую букву константного массива символов, но не может ли что-то другое, например, другая переменная перезаписать часть массива символов в памяти? Таким образом, заставляя str быть логически недействительным?

Ответы [ 7 ]

7 голосов
/ 11 октября 2009

В эти дни строковые константы помещаются в секции только для чтения вашего двоичного файла. Если вы попытаетесь записать адрес в разделе, доступном только для чтения, блок управления памятью ЦП вызовет ошибку, а ваше приложение получит нарушение прав доступа, ошибку сегментации или другое поведение, зависящее от операционной системы.

Кроме того, компиляторы предупреждают, если вы объявляете тип строковой константы неконстантным.

6 голосов
/ 11 октября 2009

но не может ли что-то другое, например, другая переменная перезаписать часть массива char в памяти?

Они не должны делать это. Причина в том, что ваш литерал C-строки является константой , и правильно он должен быть объявлен как один:

char const* str = "This is a c-styled string";

Ваш (неконстантный) код допускается только из-за несовместимости с устаревшим кодом C. Попытки изменить данные приводят к неопределенному поведению.

3 голосов
/ 11 октября 2009

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

Люди не должны использовать C, если они не знают, что делают. Также как они не должны использовать бензопилу без надлежащей подготовки. Весь смысл C был языком системного программирования. Это дает вам полную силу делать то, что вы хотите. И с властью приходит ответственность.

1 голос
/ 11 октября 2009

Они так же безопасны, как и ваши практики программирования.Пока вы знаете, как правильно с ними работать, они совершенно безопасны.Для тех, чей стиль программирования заставляет думать о слоне в посудной лавке, такие строки могут быть небезопасными.Но тогда то же самое можно сказать и обо всех языках C / C ++.

Ваш исходный пример однострочного объявления уже страдает от небезопасных проблем стиля.И в C, и в C ++ строковые литералы являются неизменяемыми l-значениями.Не стоит создавать [долговечные] неконстантные указатели, указывающие на такие литералы.Обычно это должно выглядеть следующим образом:

const char *str = "This is a c-styled string";

Обратите внимание на дополнительный const.

(Это конкретное правило не всегда соблюдается в C, но обычно его необходимо нарушать только в каком-то хорошо контролируемом локализованном идиоматическом коде.)

1 голос
/ 11 октября 2009

Это небезопасно. Но так же, как и любые другие вещи в C / C ++. Вы можете легко перезаписать часть памяти, используемой другим объектом.

0 голосов
/ 11 октября 2009

Зависит от того, что вы подразумеваете под "безопасным".

Они не менее безопасны по своей природе, чем любое другое использование указателей в C / C ++. Указатели требуют, чтобы вы были очень осторожны с памятью в целом.

0 голосов
/ 11 октября 2009

На самом деле не делайте этого:

int *foo = 0x1234;
byte[] bytes = (byte[]) foo;
bytes[0] = 0x56;

printf("%d\n", *foo);

При этом любой указатель опасен при неправильном использовании.

...