инварианты программы останутся нетронутыми
(т.е. не будут повреждены структуры данных) и не будет никаких утечек ресурсов. Функ
ции, обеспечивающие строгую гарантию, гарантируют, что, даже если будет сгенериро
вано исключение, состояние программы останется тем же, что и до вызова функции.
Говоря о функциональном объекте, я обычно имею в виду объект типа, поддержи
вающего функцию-член operator (). Другими словами, это объект, действующий, как
функция. Иногда я использую термин в несколько более общем смысле для обозначения
чего уrодно, что может быть вызвано с использованием синтаксиса вызова функции, не
являющейся членом (т.е. function Name (arguments) ). Это более широкое определе
ние охватывает не только объекты, поддерживающие operator (), но и функции и ука
затели на функции в стиле С. (Более узкое определение происходит из С++98, более ши
рокое - из C++ll.) Дальнейшее обобщение путем добавления указателей на функции
члены дает то, что известно как вызываемый объект (callaЫe object). Вообще говоря,
-
18
В ведение
можно иrнорировать эти тонкие отличия и просто рассматривать функциональные и вы
зываемые объекты как сущности в С++, которые моrут быть вызваны с помощью неко
торой разновидности синтаксиса вызова функции.
Функциональные объекты, создаваемые с помощью лямбда-выражений, известны как
замь1кания (closures). Различать лямбда-выражения и замыкания, ими создаваемые, при
ходится редко, так что я зачастую rоворю о них обоих как о лямбдах (lambda). Точно так
же я редко различаю шаблоны функций (fuпction templates) (т.е. шаблоны, которые rе
нерируют функции) и шаблонные функции (template ftшctions) (т.е. функции, сrенериро
ванные из шаблонов функций). То же самое относится к шаблонам классов и шаблонным
классам.
Мноrие сущности в С++ моrут быть как объявлены, так и определены. Объявления
вводят имена и типы, не детализируя информацию о них, такую как их местоположение
в памяти или реализация:
extern int
х;
class Widget ;
11 Объявление объекта
11 Объявление класс а
bool func ( const Widget& W); 11 Объявление функции
enшn class Color;
11 Объявление перечисления
11 с областью видимости
11 ( см. раздел 3.4)
Определение предоставляет информацию о расположении в памяти и деталях реализации:
int
х;
cla ss Widget
)
11 Определение объекта
11 Определение класса
;
bool func ( const Widget& w)
{ return w . size ( ) < 1 0 ; 1 // Определение функции
enurn class Color
{ Yellow, Red, Blue f ;
11 Определение перечисления
Определение можно квалифицировать и как объявление, так что, если только то, что
нечто представляет собой определение, не является действительно важным, я предпочи
таю использовать термин "объявление·:
Сигнатуру функции я определяю как часть ее объявления, определяющую типы
параметров и возвращаемый тип. Имена функции и параметров значения не име
ют. В приведенном выше примере сиrнатура функции func представляет собой
bool (const Widget&) . Исключаются элементы объявления функции, отличные от ти
пов ее параметров и возвращаемоrо типа (например. noexcept или constexpr, если
таковые имеются). (Модификаторы noexcept и constexpr описаны в разделах 3.8
В ведение
19
и 3.9.) Официальное определение термина "сигнатура" несколько отличается от моего,
но в данной книге мое определение оказывается более полезным. (Официальное опреде
ление иногда опускает возвращаемый тип.)
Новый стандарт С++ в общем случае сохраняет корректность кода, написанного для бо
лее старого стандарта, но иногда Комитет по стандартизации не рекомендует применять те
или иные возможности. Такие возможности находятся в "камере смертников" стандартиза
ции и могут быть убраны из новых версий стандарта. Компиляторы могут предупреждать
об использовании программистом таких устаревших возможностей (но могут и не делать
этого), но в любом случае их следует избегать. Они могут не только привести в будущем
к головной боли при переносе, но и в общем случае они ниже по качеству, чем возмож
ности, заменившие их. Например, st d : : a ut o _pt r не рекомендуется к применению
в C++ l l , поскольку std:: unique_pt r выполняет ту же работу, но лучше.
Иногда стандарт гласит, что результатом операции является неопределенное поведе
ние (undefined behavior). Это означает, что поведение времени выполнения непредсказу
емо, и от такой непредсказуемости, само собой разумеется, следует держаться подальше.
Примеры действий с неопределенным поведением включают использование квадратных
скобок ( []) для индексации за границами std: :vec t o r, разыменование неинициали
зированного итератора или гонку данных (т.е. когда два или более потоков, как минимум
один из которых выполняет запись, одновременно обращаются к одному и тому же ме
сту в памяти).
Я называю встроенный указатель, такой как возвращаемый оператором new, обычным
указателем (raw pointer). Противоположностью обычному указателю является интеллек
туальный указатель (smart pointer). Интеллектуальные указатели обычно
Последние комментарии
45 минут 51 секунд назад
1 час 18 минут назад
2 часов 15 минут назад
17 часов 16 минут назад
19 часов 50 минут назад
20 часов 19 минут назад