Строки. Обращение к символам

   
На этом шаге мы рассмотрим способы и особенности обращения к отдельным символам строки.

   
Строки предоставляют возможность чтения и записи хранящихся в них символов. Обращение к отдельному символу производится одним из двух
способов: оператором индексирования [] или функцией at(). Обе операции возвращают символ в позиции с заданным индексом. Как обычно,
первому символу соответствует индекс 0, а последнему - индекс length()-l. Тем не менее существуют и различия.

  • Оператор [] не проверяет правильность индекса, передаваемого в аргументе, а функция at() выполняет такую проверку. При вызове функции
    at() с недействительным индексом генерируется исключение out_of_range. При вызове оператора [] с недействительным индексом
    возможны непредсказуемые последствия - скажем, недопустимые обращения к памяти, которые становятся причиной неприятных побочных эффектов,
    или аварийное завершение программы (кстати, это относительно удачный вариант, по крайней мере, вы будете знать, что в программе что-то не так).
  • Для константной версии оператора [] позиция за последним символом считается действительной. В этом случае текущее количество символов
    является допустимым индексом. Оператор возвращает значение, сгенерированное конструктором по умолчанию для типа символов. Следовательно,
    для объектов типа string возвращается символ \0.

   
Во всех остальных случаях (для неконстантной версии оператора [] и функции at()) индекс, равный текущему количеству символов,
считается недействительным. Его использование приводит к исключениям или непредсказуемым последствиям. Пример:

const std::string cs('nico"); // cs содержит символы n, i, c, o
std.rstring s("abcde");       // s содержит символы a, b, c, d, e
s[2]              // Символ с
s.at(2)           // Символ с
s[100]            // ОШИБКА: непредсказуемые последствия
s.at(100)         // Исключение out_of_range
s[s.length()]     // ОШИБКА: непредсказуемые последствия
cs[cs.length()]   // Символ \0
s.at(s.length())  // Исключение out_of_range
cs.at(s.length()) // Исключение out_of_range

   
Чтобы программа могла изменять отдельные символы строки, неконстантные версии [] и at() возвращают ссылки на символы. Помните, что
при перераспределении памяти ссылки становятся недействительными:

std::string s("abcde");     // s содержит символы a, b, c, d, e
char& r = s[2];	            // Ссылка на третий символ
char* p = &s[3];	    // Указатель на четвертый символ
r = 'X';                    // ОК. s содержит символы a, b, X, d, e
*р = 'Y';	            // ОК. s содержит символы a, b, X, Y, e
s = "new long value";       // При перераспределении памяти r и р
                            // становятся недействительными
r = 'X';                    // ОШИБКА: непредсказуемые последствия
*р = 'Y';                   // ОШИБКА: непредсказуемые последствия

   
Для предотвращения ошибок времени выполнения необходимо зарезервировать достаточную емкость функцией reserve() перед инициализацией
r и р.

   
Ссылки и указатели, ссылающиеся на символы строки, становятся недействительными при выполнении следующих операций:

  • обмен значений функцией swap();
  • чтение нового значения оператором >> или функцией getllne();
  • экспорт содержимого строки функцией data() или c_str();
  • вызов любой из неконстантных функций класса at(), begin(), rbegin(), end() или rend() без оператора [];
  • вызов оператора [] после любой из функций at(), begln(), rbegln(), end() или rend().

   
Данные условия также относятся к итераторам.

   
На следующем шаге мы рассмотрим операции стравнения.



Вы можете оставить комментарий, или Трекбэк с вашего сайта.

Оставить комментарий