В этом разделе описывается содержимое C++ standard library, как правильно сформированная программа на C ++ использует библиотеку и как соответствующая реализация может предоставлять сущности в библиотеке.
Следующие подразделы описывают definitions, метод descriptionи organization библиотеки. Пункт [requirements], Пункты [language.support] по [thread]и Приложение [depr] определяют содержимое библиотеки, а также требования и ограничения библиотеки как для правильно сформированных программ C ++, так и для соответствующих реализаций.
Подробные спецификации для каждого из компонентов библиотеки приведены в разделах [language.support]-[thread], как показано в таблице 15.
Пункт | Категория | |
[language.support] | Библиотека языковой поддержки | |
[diagnostics] | Библиотека диагностики | |
[utilities] | Библиотека общих утилит | |
[strings] | Библиотека строк | |
[localization] | Библиотека локализации | |
[containers] | Библиотека контейнеров | |
[iterators] | Библиотека итераторов | |
[algorithms] | Библиотека алгоритмов | |
[numerics] | Библиотека чисел | |
[input.output] | Библиотека ввода / вывода | |
[re] | Библиотека регулярных выражений | |
[atomics] | Библиотека атомарных операций | |
[thread] | Библиотека поддержки потоков |
language support library Содержит компоненты, которые требуются определенные части языка C ++, таких как распределение памяти ([expr.new], [expr.delete]) и exception processing.
diagnostics library Обеспечивает последовательную основу для сообщения об ошибках в программе C ++, в том числе предварительно определенных классов исключений.
general utilities library Включает в себя компоненты , используемые другими элементы библиотеки, такие как предопределенный распределитель для хранения dynamic storage managementи компонентов , используемые в качестве инфраструктуры в программах C ++, такие как кортежи, функции оберток и время объекты.
strings library Обеспечивает поддержку для манипулирования текст представлен в виде последовательности типа char, последовательностей типа char16_t, последовательностей типа char32_t, последовательностей типа wchar_tи последовательности любого другого символа-подобного типа.
localization library Обеспечивает расширенную поддержку интернационализации для обработки текста.
Библиотеки containers, iteratorsи algorithms предоставляют программе на C ++ доступ к подмножеству наиболее широко используемых алгоритмов и структур данных.
numerics library Предоставляет числовые алгоритмы и сложные компоненты номерных , которые расширяют поддержку цифровой обработки. valarray Компонент обеспечивает поддержку для nобработки -при-времени, потенциально реализован в виде параллельных операций на платформах , которые поддерживают такую обработку. Компонент случайных чисел предоставляет средства для генерации псевдослучайных чисел.
input/output library Обеспечивают iostream компоненты , которые являются основным механизмом для C ++ ввода и вывода программы. Их можно использовать с другими элементами библиотеки, особенно со строками, языками и итераторами.
Это atomic operations library позволяет более детализированный одновременный доступ к общим данным, чем это возможно с блокировками.
thread support library Предоставляет компоненты для создания и управления потоками, в том числе взаимного исключения и interthread связи.
Стандартная библиотека C ++ также предоставляет возможности стандартной библиотеки C, настроенные соответствующим образом для обеспечения безопасности статического типа.
Описание многих библиотечных функций зависит от стандартной библиотеки C для семантики этих функций. В некоторых случаях подписи, указанные в этом международном стандарте, могут отличаться от подписей в стандартной библиотеке C, и в этом международном стандарте могут быть объявлены дополнительные перегрузки, но поведение и предварительные условия (включая любые предварительные условия, подразумеваемые использованием restrict Квалификатор ISO C ) являются такими же, если не указано иное.
[ Note: Пункт [intro.defs] определяет дополнительные термины, используемые в других частях настоящего международного стандарта. ] — end note
поток (описанный в разделе [input.output]), который может стремиться к любой целостной позиции в пределах длины потока
[ Note: Каждый поток с произвольной позицией также является потоком репозиции. ] — end note
& Лангле; Статьи [strings], [localization], [input.output]и [re]& rangle; любой объект , который, когда обрабатывает последовательно, может представлять текст
[ Note:
термин не означает только
char,
char16_t,
char32_t, и
wchar_t
объекты, но любое значение , которое может быть представлено типом , который обеспечивает определения , указанные в этих пунктах.
] — end note
класс или тип, используемый для представления
[
Он используется для одного из параметров шаблона строки, iostream и шаблонов классов регулярных выражений. Тип контейнера символов - это .
]character
Note: POD type — end note
an operator function для любого из операторов equality или relational
группа библиотечных сущностей, напрямую связанных как члены, параметры или возвращаемые типы
[ Note:
Например, шаблон класса и шаблоны
basic_string
функций, не являющихся членами, которые работают со строками, называются
string component.
] — end note
выражение, оценка которого как часть выражения a conditional-expression CE не помешает CE быть core constant expression
один или несколько потоков не могут продолжить выполнение, потому что каждый из них заблокирован, ожидая, пока один или несколько других потоков удовлетворят некоторому условию
& langle; реализация & rangle; любое конкретное поведение, обеспечиваемое реализацией, в рамках required behavior
& langle; спецификация & rangle; описание replacement function и handler function семантика
прямая инициализация ([dcl.init]), которая не является инициализацией списка ([dcl.init.list])
a
non-reserved function
, определение которого может быть предоставлено программой C ++
[ Note:
Программа C ++ может назначать функцию-обработчик в различных точках своего выполнения, предоставляя указатель на функцию при вызове любой из библиотечных функций, устанавливающих функции-обработчики (пункт [language.support]).
] — end note
шаблоны, определенные в Пункте [input.output], которые принимают два аргумента шаблона
[ Note:
Аргументы называются
charT
и
traits. Аргумент
charT
- это класс-контейнер символов, а аргумент
traits
- это класс, который определяет дополнительные характеристики и функции символьного типа, представленного
charT
необходимыми для реализации шаблонов классов iostream.
] — end note
class member function кроме конструктора, оператор присваивания или деструктор , который изменяет состояние объекта класса
присвоение rvalue некоторого типа объекта изменяемому lvalue того же типа
прямая инициализация объекта некоторого типа с rvalue того же типа
последовательность значений, character type которые предшествуют завершающему значению типа нулевого символа charT()
a, class member function который обращается к состоянию объекта класса, но не изменяет это состояние
[ Note:
Функции-наблюдатели указаны как
const
функции-члены ([class.this]).
] — end note
тип объекта, тип функции, не имеющий cv-квалификаторов или a ref-qualifier, или ссылочный тип [ Note: термин описывает тип, на который может быть создана ссылка, включая ссылочные типы. ] — end note
a
non-reserved function
, определение которого предоставляется программой C ++
[ Note:
Только одно определение для такой функции действует на время выполнения программы в результате создания программы ([lex.phases]) и разрешения определений всех единиц перевода ([basic.link]).
] — end note
поток (описанный в пункте [input.output]), который может стремиться к позиции, с которой ранее сталкивались
описание
replacement function
и
handler function
семантика, применимые как к поведению, обеспечиваемому реализацией, так и к поведению любого такого определения функции в программе
[ Note:
Если такая функция, определенная в программе C ++, не соответствует требуемому поведению при выполнении, поведение не определено. ]
— end note
функция, указанная как часть стандартной библиотеки C ++, которая должна быть определена реализацией
[ Note:
Если программа C ++ предоставляет определение для какой-либо зарезервированной функции, результаты не определены. ]
— end note
алгоритм, который сохраняет, в зависимости от конкретного алгоритма, порядок элементов
[ Note: Требования к стабильным алгоритмам приведены в [algorithm.stable]. ] — end note
класс, который инкапсулирует набор типов и функций, необходимых для шаблонов классов и шаблонов функций для управления объектами типов, для которых они созданы
значение объекта, которое не указано, за исключением того, что инварианты объекта выполняются, и операции с объектом ведут себя так, как указано для его типа
[ Example: Если объект x типа std::vector<int> находится в допустимом, но неуказанном состоянии, x.empty() может вызываться безоговорочно и x.front() может быть вызван только если x.empty() вернется
false. ] — end example
В этом подпункте описаны соглашения, используемые для определения стандартной библиотеки C ++. [structure] описывает структуру нормативных разделов [language.support] через [thread] и Приложение [depr]. [conventions] описывает другие редакционные соглашения.
Каждое предложение библиотеки содержит следующие элементы, если применимо:155
Резюме
Требования
Подробные характеристики
Ссылки на стандартную библиотеку C
Для экономии места элементы, не относящиеся к пункту, опускаются. Например, если в разделе не указаны какие-либо требования, подпункта «Требования» не будет.
Резюме предоставляет синопсис категории и вводит подпункты первого уровня. В каждом подпункте также приводится сводка, в которой перечислены заголовки, указанные в подпункте, и объекты библиотеки, представленные в каждом заголовке.
Пункты, помеченные «Примечание (и):» или «Пример (ы):», являются информативными, остальные параграфы являются нормативными.
Требования описывают ограничения, которым должна соответствовать программа C ++, расширяющая стандартную библиотеку. Такие расширения обычно являются одним из следующих:
Аргументы шаблона
Производные классы
Контейнеры, итераторы и алгоритмы, соответствующие соглашению об интерфейсе
Компоненты string и iostream используют явное представление операций, требуемых от аргументов шаблона. Они используют шаблон класса char_traits для определения этих ограничений.
Требования соглашения об интерфейсе сформулированы как можно более широко. Вместо того , заявив , что «класс X должен определить функцию - член operator++()», интерфейс требует «для любого объекта x класса X, ++x определяется». То есть, является ли оператор членом, не указано.
Требования сформулированы в виде четко определенных выражений, которые определяют действительные термины типов, удовлетворяющих требованиям. Для каждого набора четко определенных требований к выражениям существует таблица, в которой указывается начальный набор допустимых выражений и их семантика. Любой общий алгоритм (пункт [algorithms]), который использует четко определенные требования к выражениям, описывается в терминах допустимых выражений для параметров его типа шаблона.
В некоторых случаях семантические требования представлены в виде кода C ++. Такой код предназначен как спецификация эквивалентности конструкции другой конструкции, не обязательно как способ реализации этой конструкции.156
Хотя в некоторых случаях приведенный код однозначно является оптимальной реализацией.
Подробные спецификации содержат следующие элементы:
название и краткое описание
синопсис (определение класса или объявление функции, в зависимости от ситуации)
ограничения на аргументы шаблона, если таковые имеются
описание инвариантов классов
описание семантики функции
Описания функций-членов класса следуют в следующем порядке (при необходимости):157
конструктор (ы) и деструктор
функции копирования, перемещения и присвоения
функции сравнения
функции-модификаторы
функции наблюдателя
операторы и другие функции, не являющиеся членами
Описание семантики функции содержит следующие элементы (при необходимости):158
Requires: предварительные условия для вызова функции
Effects: действия, выполняемые функцией
Synchronization: операции синхронизации ([intro.multithread]), применимые к функции
Postconditions: наблюдаемые результаты, установленные функцией
Returns: описание значений, возвращаемых функцией
Throws: любые исключения, созданные функцией, и условия, которые могут вызвать исключение
Complexity: временная и / или пространственная сложность функции
Remarks: дополнительные семантические ограничения на функцию
Error conditions: условия ошибок для кодов ошибок, сообщаемых функцией
Каждый раз, когда Effects элемент указывает, что семантика некоторой функции F представляет собой Equivalent to некоторую кодовую последовательность, различные элементы интерпретируются следующим образом. Если Fсемантика определяет Requires элемент, то это требование логически налагается до equivalent-to семантики. Далее, семантика кодовой последовательности определяется Requires, Effects, Synchronization, Postconditions, Returns, Throws, Complexity, Remarks, и Error conditions указана для функциональных вызовов , содержащихся в кодовой последовательности. Значение, возвращаемое из F , определяется элементом F's Returns , или, если F не имеет Returns элемента,void невозврат из F задается return операторами в кодовой последовательности. Если Fсемантика содержит элемент Throws, Postconditionsили Complexity , то он заменяет любые вхождения этого элемента в кодовой последовательности.
Для незарезервированных функций замены и обработчика Clause [language.support] определяет два поведения для рассматриваемых функций: их обязательное поведение и поведение по умолчанию. default behavior Описывает определение функции , предоставляемой реализации. required behavior Описывает семантику определения функции , представленное либо реализации или программой C ++. Если в описании не делается явных различий, описанное поведение является обязательным.
Если формулировка требования сложности требует отрицательного числа операций, фактическое требование - нулевое количество операций.159
Требования к сложности, указанные в разделах библиотеки, являются верхними границами, и реализации, которые обеспечивают более высокие гарантии сложности, удовлетворяют этим требованиям.
Условия ошибки определяют условия, при которых функция может выйти из строя. Условия перечислены вместе с подходящим объяснением как enum class errc константы ([syserr]).
Для экономии места элементы, не относящиеся к классу, опускаются. Например, если в классе не указаны какие-либо функции сравнения, подпункта «Функции сравнения» не будет.
Для экономии места элементы, не относящиеся к функции, опускаются. Например, если функция не определяет никаких дополнительных предварительных условий, Requires: абзаца не будет .
В некоторых случаях это упрощает представление требований к сложности.
В этом подпункте описывается несколько редакционных соглашений, используемых для описания содержимого стандартной библиотеки C ++. Эти соглашения предназначены для описания implementation-defined types, и member functions.
Подпункты Требования могут описывать имена, которые используются для определения ограничений для аргументов шаблона.160 Эти имена используются в разделах библиотеки для описания типов, которые могут быть предоставлены в качестве аргументов программой C ++ при создании экземпляров компонентов шаблона из библиотеки.
Некоторые типы, определенные в разделе [input.output] , используются для описания типов, определяемых реализацией. Они основаны на других типах, но с дополнительными ограничениями.
Примеры из [utility.requirements] включают в себя: EqualityComparable, LessThanComparable, CopyConstructible. Примеры [iterator.requirements] включают: InputIterator, ForwardIterator.
Несколько типов , определенных в пунктах [language.support] через [thread] и Приложение [depr] , которые используются в качестве параметров функции или возврата типов определяются для целей изложения только для того , чтобы захватить их языковую связь. За объявлениями таких типов следует комментарий, оканчивающийся на exposition only. [ Example:
namespace std { extern "C" using some-handler = int(int, void*, double); // exposition only }
Заполнитель типа some-handler теперь можно использовать для указания функции, которая принимает параметр обратного вызова с привязкой к языку C. ] — end example
Существует несколько типов , определенных в пункте [input.output] являются enumerated types. Каждый перечислимый тип может быть реализован как перечисление или как синоним перечисления.161
Перечислимый тип enumerated можно записать:
enum enumerated { \textit{V}0, \textit{V}1, \textit{V}2, \textit{V}3, ..... }; inline const \textit{enumerated C}0(\textit{V}0); inline const \textit{enumerated C}1(\textit{V}1); inline const \textit{enumerated C}2(\textit{V}2); inline const \textit{enumerated C}3(\textit{V}3); .....
Здесь имена \textit{C}0, \textit{C}1и т.д. , представляют enumerated elements для этого конкретного перечислимого типа. Все такие элементы имеют разные значения.
Например, целочисленный тип с постоянными целочисленными значениями ([basic.fundamental]).
Несколько типов , определенных в пунктах [language.support] через [thread] и Дополнением [depr] являются bitmask types. Каждый тип битовой маски может быть реализован как перечислимый тип, который перегружает определенные операторы, как целочисленный тип или как bitset.
Тип битовой маски bitmask можно записать:
// For exposition only. // int_type is an integral type capable of representing all values of the bitmask type. enum bitmask : int_type { \textit{V}0 = 1 << 0, \textit{V}1 = 1 << 1, \textit{V}2 = 1 << 2, \textit{V}3 = 1 << 3, ..... }; inline constexpr \textit{bitmask C}0(\textit{V}0); inline constexpr \textit{bitmask C}1(\textit{V}1); inline constexpr \textit{bitmask C}2(\textit{V}2); inline constexpr \textit{bitmask C}3(\textit{V}3); ..... constexpr bitmask operator&(bitmask X, bitmask Y) { return static_cast<bitmask>( static_cast<int_type>(X) & static_cast<int_type>(Y)); } constexpr bitmask operator|(bitmask X, bitmask Y) { return static_cast<bitmask>( static_cast<int_type>(X) | static_cast<int_type>(Y)); } constexpr bitmask operator^(bitmask X, bitmask Y){ return static_cast<bitmask>( static_cast<int_type>(X) ^ static_cast<int_type>(Y)); } constexpr bitmask operator~(bitmask X){ return static_cast<bitmask>(~static_cast<int_type>(X)); } bitmask& operator&=(bitmask& X, bitmask Y){ X = X & Y; return X; } bitmask& operator|=(bitmask& X, bitmask Y) { X = X | Y; return X; } bitmask& operator^=(bitmask& X, bitmask Y) { X = X ^ Y; return X; }
Здесь имена \textit{C}0, \textit{C}1и т.д. , представляют bitmask elements для этого конкретного типа Bitmask. Все такие элементы имеют различные ненулевые значения, такие что для любой пары \textit{C}i и \textit{C}j где i≠j, Ci & Ci отличен от нуля и Ci & Cj равен нулю. Кроме того, значение 0 используется для представления объекта empty bitmask, в котором не установлены элементы битовой маски.
Следующие термины применяются к объектам и значениям типов битовых масок:
Чтобы set получить значение Y в объекте X , нужно оценить выражение X |= Y.
Чтобы clear получить значение Y в объекте X , нужно оценить выражение X &= ~Y.
Значение Y is set в объекте, X если выражение не X & Y равно нулю.
Стандартная библиотека C широко использует символы и последовательности символов, которые следуют нескольким единым соглашениям:
A letter - это любая из 26 строчных или 26 прописных букв в базовом наборе символов выполнения.
Это decimal-point character (однобайтовый) символ, используемый функциями, которые преобразуют (однобайтовую) последовательность символов в значение одного из типов с плавающей запятой. Он используется в последовательности символов для обозначения начала дробной части. Оно представлено в пунктах [language.support] через [thread] и Приложении [depr] периодом, '.', который также его значение в "C" местности, но может изменяться во время выполнения программы с помощью вызова setlocale(int, const char*),162 или путем изменения к locale объекту, как это описано в пунктах [locales] и [input.output].
character sequence Является , array object A что может быть объявлено как T A[N], где T любой из типов char, unsigned charили signed char ([basic.fundamental]), необязательно квалифицирован по любой комбинации const или volatile. Начальные элементы массива имеют определенное содержимое вплоть до элемента, определенного некоторым предикатом. Последовательность символов может быть обозначена значением указателя S , указывающим на ее первый элемент.
A null-terminated byte stringили ntbs - это последовательность символов, элемент с самым высоким адресом и определенным содержимым которой имеет нулевое значение ( terminating null символ); ни один другой элемент в последовательности не имеет нулевого значения.163
length А. Н. НТБ является количество элементов , которые предшествуют завершающий нулевой символ. An НТБ имеет нулевую длину.empty
value А.Н. НТБ представляет собой последовательность значений элементов до и включая завершающий нулевой символ.
Многие из объектов, которыми манипулируют сигнатуры функций, объявленные в, <cstring> являются последовательностями символов или ntbs . Размер некоторых из этих последовательностей символов ограничен значением длины, которое поддерживается отдельно от последовательности символов.
Строковый литерал, например "abc", является статическим ntbs .
A null-terminated multibyte string, или ntmbs , представляет собой ntbs, который составляет последовательность допустимых многобайтовых символов, начинающуюся и заканчивающуюся в начальном состоянии сдвига.165
An НТБ , который содержит только символы из базового набора символов исполнения также является ntmbs . В этом случае каждый многобайтовый символ состоит из одного байта.
Ради изложения Морозы [language.support] через [thread] и приложение [depr] не описывают копирование / перемещение конструкторов, оператор присваивания, или (невиртуальные) деструкторы с той же самой очевидной семантикой, которые могут быть получены по умолчанию ([class.ctor], [class.dtor], [class.copy]). Не указано, предоставляет ли реализация явные определения для таких сигнатур функций-членов или для виртуальных деструкторов, которые могут быть сгенерированы по умолчанию.
Ради наглядности в предложениях библиотеки конструкторы иногда аннотируются с помощью EXPLICIT. Такой конструктор условно объявляется как явный или неявный ([class.conv.ctor]). [ Note: Обычно это реализуется путем объявления двух таких конструкторов, максимум один из которых участвует в разрешении перегрузки. ] — end note
Пункты [language.support] до [thread] и Приложение [depr] не определяют представление классов и намеренно опускают спецификацию class members. Реализация может определять статические или нестатические члены класса, или и то, и другое, по мере необходимости для реализации семантики функций-членов, указанных в разделах [language.support] по [thread] и в приложении [depr].
В целях пояснения некоторые подпункты предоставляют репрезентативные объявления и семантические требования для частных членов классов, которые соответствуют внешним спецификациям классов. За объявлениями для таких членов следует комментарий, который заканчивается exposition onlyследующим образом:
streambuf* sb; // exposition only
В этом подпункте указаны требования, которые применяются ко всей стандартной библиотеке C ++. Пункты [language.support] до [thread] и Приложение [depr] определяют требования отдельных организаций в библиотеке.
Требования, указанные в терминах взаимодействия между потоками, не применяются к программам, имеющим только один поток выполнения.
В этом подпункте [organization] описывается содержимое и организация библиотеки, [using] описывается, как правильно сформированные программы C ++ получают доступ к объектам библиотеки, [utility.requirements] описываются ограничения на типы и функции, используемые со стандартной библиотекой C ++, [constraints] описываются ограничения на правильно сформированные программы на C ++ и [conforming] описываются ограничения на соответствующие реализации.
[contents] описывает сущности и макросы, определенные в стандартной библиотеке C ++. [headers] перечисляет заголовки стандартной библиотеки и некоторые ограничения на эти заголовки. [compliance] перечисляет требования к автономной реализации стандартной библиотеки C ++.
Стандартная библиотека C ++ предоставляет определения для сущностей и макросов, описанных в резюме заголовков стандартной библиотеки C ++ ([headers]).
Все объекты библиотеки, кроме operator new и operator delete , определены в пространстве имен std или пространствах имен, вложенных в пространство имен std. Не указано, объявляются ли имена, объявленные в определенном пространстве имен, непосредственно в этом пространстве имен или во встроенном пространстве имен внутри этого пространства имен.166167
Всякий раз, когда x упоминается имя, определенное в стандартной библиотеке, x предполагается , что имя полностью определено как ::std::x, если явно не указано иное. Например, если Effects: раздел для библиотечной функции F описывается как вызывающая библиотечная функция G,::std::G имеется в виду функция .
Заголовки стандартной библиотеки C (Приложение [depr.c.headers]) также определяют имена в глобальном пространстве имен, в то время как заголовки C ++ для средств библиотеки C ([headers]) могут также определять имена в глобальном пространстве имен.
Это дает разработчикам свободу использовать встроенные пространства имен для поддержки нескольких конфигураций библиотеки.
Каждый элемент стандартной библиотеки C ++ объявлен или определен (при необходимости) в файле header.168
Стандартная библиотека C ++ предоставляет C++ library headers, как показано в Табл 16.
<algorithm> | <future> | <numeric> | <strstream> |
<any> | <initializer_list> | <optional> | <system_error> |
<array> | <iomanip> | <ostream> | <thread> |
<atomic> | <ios> | <queue> | <tuple> |
<bitset> | <iosfwd> | <random> | <type_traits> |
<chrono> | <iostream> | <ratio> | <typeindex> |
<codecvt> | <istream> | <regex> | <typeinfo> |
<complex> | <iterator> | <scoped_allocator> | <unordered_map> |
<condition_variable> | <limits> | <set> | <unordered_set> |
<deque> | <list> | <shared_mutex> | <utility> |
<exception> | <locale> | <sstream> | <valarray> |
<execution> | <map> | <stack> | <variant> |
<filesystem> | <memory> | <stdexcept> | <vector> |
<forward_list> | <memory_resource> | <streambuf> | |
<fstream> | <mutex> | <string> | |
<functional> | <new> | <string_view> |
Возможности стандартной библиотеки C представлены в дополнительных заголовках, показанных в таблице 17.169
<cassert> | <cinttypes> | <csignal> | <cstdio> | <cwchar> |
<ccomplex> | <ciso646> | <cstdalign> | <cstdlib> | <cwctype> |
<cctype> | <climits> | <cstdarg> | <cstring> | |
<cerrno> | <clocale> | <cstdbool> | <ctgmath> | |
<cfenv> | <cmath> | <cstddef> | <ctime> | |
<cfloat> | <csetjmp> | <cstdint> | <cuchar> |
За исключением указанных в пунктах [library] через [thread] и приложение [depr], содержание каждого заголовка cname такое же , как и у соответствующего заголовка , name.h как указано в разделе C standard library. Однако в стандартной библиотеке C ++ объявления (за исключением имен, которые определены как макросы в C) находятся в пределах namespace scope пространства имен std. Не указано, были ли эти имена (включая любые перегрузки, добавленные в разделах [language.support] по [thread] и Приложение [depr]) сначала объявлены в области глобального пространства имен, а затем std явно введены в пространство имен using-declarations.
Имена, которые определены как макросы в C, должны определяться как макросы в стандартной библиотеке C ++, даже если C предоставляет лицензию на реализацию в качестве функций. [ Note: Имена , определенные как макросы в C включают в себя следующее: assert, offsetof, setjmp, va_arg, va_end, и va_start. ] — end note
Имена, которые определены как функции в C, должны быть определены как функции в стандартной библиотеке C ++.170
Идентификаторы, которые являются ключевыми словами или операторами в C ++, не должны определяться как макросы в заголовках стандартной библиотеки C ++.171
[depr.c.headers], Заголовки стандартной библиотеки C, описывает эффекты использования формы name.h (заголовок C) в программе на C ++.172
Приложение K к стандарту C описывает большое количество функций с соответствующими типами и макросами, которые «способствуют более безопасному и безопасному программированию», чем многие традиционные функции библиотеки C. Имена функций имеют суффикс _s; большинство из них предоставляют ту же услугу, что и функция библиотеки C с именем без суффиксов, но обычно принимают дополнительный аргумент, значение которого является размером массива результатов. Если включен какой-либо заголовок C ++, это определяется реализацией, объявлено ли какое-либо из этих имен в глобальном пространстве имен. (Ни один из них не объявлен в пространстве имен std.)
В таблице 18 перечислены имена Приложения K, которые могут быть объявлены в каком-либо заголовке. На эти имена также распространяются ограничения [macro.names].
abort_handler_s | mbstowcs_s | strncat_s | vswscanf_s |
asctime_s | memcpy_s | strncpy_s | vwprintf_s |
bsearch_s | memmove_s | strtok_s | vwscanf_s |
constraint_handler_t | memset_s | swprintf_s | wcrtomb_s |
ctime_s | printf_s | swscanf_s | wcscat_s |
errno_t | qsort_s | tmpfile_s | wcscpy_s |
fopen_s | RSIZE_MAX | TMP_MAX_S | wcsncat_s |
fprintf_s | rsize_t | tmpnam_s | wcsncpy_s |
freopen_s | scanf_s | vfprintf_s | wcsnlen_s |
fscanf_s | set_constraint_handler_s | vfscanf_s | wcsrtombs_s |
fwprintf_s | snprintf_s | vfwprintf_s | wcstok_s |
fwscanf_s | snwprintf_s | vfwscanf_s | wcstombs_s |
getenv_s | sprintf_s | vprintf_s | wctomb_s |
gets_s | sscanf_s | vscanf_s | wmemcpy_s |
gmtime_s | strcat_s | vsnprintf_s | wmemmove_s |
ignore_handler_s | strcpy_s | vsnwprintf_s | wprintf_s |
L_tmpnam_s | strerror_s | vsprintf_s | wscanf_s |
localtime_s | strerrorlen_s | vsscanf_s | |
mbsrtowcs_s | strlen_s | vswprintf_s |
Заголовок не обязательно является исходным файлом, и последовательности, разделенные < и > в именах заголовков, не обязательно являются допустимыми именами исходного файла ([cpp.include]).
Это намеренное , что не существует C ++ заголовок для любого из этих заголовков C: , , .<stdatomic.h><stdnoreturn.h><threads.h>
Это запрещает практику, разрешенную в C, по предоставлению макроса маскировки в дополнение к прототипу функции. Единственный способ добиться эквивалентного встроенного поведения в C ++ - предоставить определение как внешнюю встроенную функцию.
В частности, включение стандартного заголовка <iso646.h> ни на <ciso646> что не влияет.
Эти ".h" заголовки сваливать все свои имена в глобальное пространство имен, в то время как новые формы сохраняют свои имена в пространстве имен std. Следовательно, новые формы являются предпочтительными формами для всех целей, кроме программ C ++, которые предназначены для строгой совместимости с C.
Определены два типа реализаций: hosted и freestanding ([intro.compliance]). Для размещенной реализации этот международный стандарт описывает набор доступных заголовков.
Автономная реализация имеет набор заголовков, определяемый реализацией. Этот набор должен включать как минимум заголовки, показанные в таблице 19.
Подпункт | Заголовок (ы) | |
<ciso646> | ||
[support.types] | Типы | <cstddef> |
[support.limits] | Свойства реализации | <cfloat> <limits> <climits> |
[cstdint] | Целочисленные типы | <cstdint> |
[support.start.term] | Начало и завершение | <cstdlib> |
[support.dynamic] | Динамическое управление памятью | <new> |
[support.rtti] | Идентификация типа | <typeinfo> |
[support.exception] | Обработка исключений | <exception> |
[support.initlist] | Списки инициализаторов | <initializer_list> |
[support.runtime] | Другая поддержка во время выполнения | <cstdarg> |
[meta] | Типовые черты | <type_traits> |
[atomics] | Атомика | <atomic> |
[depr.cstdalign.syn], [depr.cstdbool.syn] | Устаревшие заголовки | <cstdalign> <cstdbool> |
Прилагаемая версия заголовка объявляет , по меньшей мере функции , , , , и ( ). Остальные заголовки, перечисленные в этой таблице, должны соответствовать тем же требованиям, что и для размещенной реализации.<cstdlib> abortatexitat_quick_exitexit quick_exit [support.start.term]
В этом разделе описывается, как программа на C ++ получает доступ к средствам стандартной библиотеки C ++. [using.headers] описывает эффекты во время фазы трансляции 4, а [using.linkage] описывает эффекты во время phase 8.
Сущности в стандартной библиотеке C ++ определены в заголовках, содержимое которых становится доступным для единицы перевода, когда она содержит соответствующие #include preprocessing directive.
Единица перевода может включать заголовки библиотеки в любом порядке (пункт [lex]). Каждый из них может быть включен более одного раза, при этом эффект не отличается от включения только один раз, за исключением того, что эффект от включения одного<cassert> или другого <assert.h> зависит каждый раз от лексически актуального определения слова .NDEBUG173
Единица трансляции должна включать заголовок только вне любого объявления или определения и должна включать заголовок лексически перед первой ссылкой в этой единице трансляции на любой из объектов, объявленных в этом заголовке. Диагностика не требуется.
Это то же самое, что и стандартная библиотека C.
Сущности в стандартной библиотеке C ++ имеют external linkage. Если не указано иное, объекты и функции имеют значение по умолчанию extern "C++" linkage ([dcl.link]).
Если имя из стандартной библиотеки C объявлена с внешним связыванием имеет или рычажный механизм реализации. Рекомендуется, чтобы реализация использовала для этой цели связь.extern "C"extern "C++"extern "C++"174
Объекты и функции, определенные в библиотеке и требуемые программой C ++, включаются в программу до ее запуска.
Единственный надежный способ объявить объект или сигнатуру функции из стандартной библиотеки C - это включить декларирующий ее заголовок, несмотря на широту, предоставленную в 7.1.4 стандарта C.
[utility.arg.requirements] описывает требования к типам и выражениям, используемым для создания экземпляров шаблонов, определенных в стандартной библиотеке C ++. [swappable.requirements] описывает требования к заменяемым типам и заменяемым выражениям. [nullablepointer.requirements] описывает требования к типам, подобным указателям, которые поддерживают нулевые значения. [hash.requirements] описывает требования к объектам хэш-функции. [allocator.requirements] описывает требования к распределителям памяти.
Определения шаблонов в стандартной библиотеке C ++ относятся к различным именованным требованиям, подробности которых изложены в таблицах 20-27. В этих таблицах T - объектный или ссылочный тип, предоставляемый программой C ++, создающей экземпляр шаблона; a,, bи c являются значениями типа (возможно const) T; s и t являются изменяемыми значениями типа T; u обозначает идентификатор; rv является значением типа T; и v является l-значением типа (возможно const) T или r-значением типа const T.
Как правило, конструктор по умолчанию не требуется. Определенные сигнатуры функций-членов класса контейнера указываются T() в качестве аргумента по умолчанию. T() должно быть четко определенным выражением ([dcl.init]), если одна из этих подписей вызывается с использованием default argument.
Выражение | Тип возврата | Требование |
a == b | конвертируемый в bool |
== является отношением эквивалентности, то есть обладает следующими свойствами:
|
Выражение | Тип возврата | Требование |
a < b | конвертируемый в bool | < это strict weak ordering relation |
Выражение | Пост-условие |
T t; | объект t инициализирован по умолчанию |
T u{}; | объект u инициализирован значением или агрегатом |
T() T{} | объект типа T инициализируется значением или агрегатом |
Выражение | Пост-условие |
T u = rv; | u эквивалентно значению rv до постройки |
T(rv) | T(rv) эквивалентно значению rv до постройки |
rvсостояние не указано [ Note: rv должно все еще соответствовать требованиям библиотечного компонента, который его использует. Операции, перечисленные в этих требованиях, должны работать, как указано, независимо от того rv , были они перемещены или нет. ] — end note |
Выражение | Пост-условие |
T u = v; | значение v не изменилось и эквивалентно u |
T(v) | значение v не изменилось и эквивалентно T(v) |
Выражение | Тип возврата | Возвращаемое значение | Пост-условие |
t = rv | T& | t | Если t и rv не относятся к одному и тому же объекту, t эквивалентно значению rv до присвоения |
rvсостояние не указано. [ Note: rv должен по-прежнему соответствовать требованиям библиотечного компонента, который его использует, независимо от того, относится ли он к одному t и rv тому же объекту или нет . Операции, перечисленные в этих требованиях, должны работать, как указано, независимо от того rv , были они перемещены или нет. ] — end note |
Выражение | Тип возврата | Возвращаемое значение | Пост-условие |
t = v | T& | t | t эквивалентно v, значение v не изменяется |
Выражение | Пост-условие |
u.~T() | Все ресурсы, принадлежащие владельцу u , возвращаются, никаких исключений не распространяется. |
В этом подпункте приведены определения заменяемых типов и выражений. В этих определениях let t обозначает выражение типа T, а let u обозначает выражение типа U.
Объект t является swappable with объектом u тогда и только тогда, когда:
выражения swap(t, u) и swap(u, t) действительны при оценке в контексте, описанном ниже, и
эти выражения имеют следующие эффекты:
объект, на который ссылается, t имеет ценность, первоначально принадлежащую u и
объект, на который ссылается, u имеет первоначальное значение t.
Контекст , в котором swap(t, u) и swap(u, t) оцениваются должен гарантировать , что бинарная функция не-член с именем «своп» выбирается с помощью overload resolution по набору кандидатов , который включает в себя:
два swap шаблона функций, определенные в <utility> и
поисковый набор, созданный argument-dependent lookup.
[ Note: Если T и U являются как фундаментальными типами, так и массивами фундаментальных типов и объявления из заголовка <utility> находятся в области видимости, общий поисковый набор, описанный выше, эквивалентен поиску по квалифицированному имени, применяемому к выражению std::swap(t, u) или по std::swap(u, t) мере необходимости. ] — end note
[ Note: Не указано, включает ли компонент библиотеки, требующий замены, заголовок, <utility> чтобы гарантировать соответствующий контекст оценки. ] — end note
Rvalue или lvalue t есть swappable тогда и только тогда, когда их t можно заменить любым rvalue или lvalue, соответственно, типа T.
Тип X удовлетворяющего любой из iterator requirements удовлетворяют требования , ValueSwappable если для любого объекта разыменовываемого x типа X, *x является заменой.
[ Example: Код пользователя может гарантировать, что оценка swap вызовов выполняется в соответствующем контексте при различных следующих условиях:
#include <utility> // Requires: std::forward<T>(t) shall be swappable with std::forward<U>(u). template <class T, class U> void value_swap(T&& t, U&& u) { using std::swap; swap(std::forward<T>(t), std::forward<U>(u)); // OK: uses “swappable with” conditions // for rvalues and lvalues } // Requires: lvalues of T shall be swappable. template <class T> void lv_swap(T& t1, T& t2) { using std::swap; swap(t1, t2); // OK: uses swappable conditions for } // lvalues of type T namespace N { struct A { int m; }; struct Proxy { A* a; }; Proxy proxy(A& a) { return Proxy{ &a }; } void swap(A& x, Proxy p) { std::swap(x.m, p.a->m); // OK: uses context equivalent to swappable // conditions for fundamental types } void swap(Proxy p, A& x) { swap(x, p); } // satisfy symmetry constraint } int main() { int i = 1, j = 2; lv_swap(i, j); assert(i == 2 && j == 1); N::A a1 = { 5 }, a2 = { -5 }; value_swap(a1, proxy(a2)); assert(a1.m == -5 && a2.m == 5); }
— end example ]
NullablePointer Типа является указателем типа типа , который поддерживает нулевые значения. Тип P соответствует требованиям, NullablePointer если:
Объект типа, инициализированный значением, P создает нулевое значение типа. Нулевое значение должно быть эквивалентно только самому себе. Инициализированный по умолчанию объект типа P может иметь неопределенное значение. [ Note: Операции с неопределенными значениями могут вызывать неопределенное поведение. ] — end note
Объект p типа P может быть contextually converted to bool. Эффект должен быть таким, как если бы p != nullptr он был оценен вместо p.
Никакая операция, которая является частью NullablePointer требований, не должна завершаться через исключение.
В таблице 28, u обозначает идентификатор, t обозначает не-const объекта типа P, a и b обозначают значение типа (возможно const) P, и np обозначает значение типа (возможно const) std::nullptr_t.
Выражение | Тип возврата | Операционная семантика |
P u(np); | Postconditions: u == nullptr | |
P u = np; | ||
P(np) | Postconditions: P(np) == nullptr | |
t = np | P& | Postconditions: t == nullptr |
a != b | контекстно конвертируемый в bool | !(a == b) |
a == np | контекстно конвертируемый в bool | a == P() |
np == a | ||
a != np | контекстно конвертируемый в bool | !(a == np) |
np != a |
Тип H соответствует Hash требованиям, если:
это function object type,
он удовлетворяет требованиям CopyConstructible и Destructible, и
выражения, показанные в таблице 29 , действительны и имеют указанную семантику.
Given Key - тип аргумента для функциональных объектов типа H, в Table 29 h - значение типа (возможно const) H, u это lvalue типа Keyи k значение типа, конвертируемого в (возможно const) Key.
Выражение | Тип возврата | Требование |
h(k) | size_t | Возвращаемое значение должно зависеть только от аргумента k на протяжении всей программы. [ Note: Таким образом, все вычисления выражения h(k) с одинаковым значением для k дают одинаковый результат для данного выполнения программы. ] [ Для двух разных значений и вероятность того, что и сравнить равные, должна быть очень мала и приближается . ] — end note Note: t1 t2 h(t1) h(t2) 1.0 / numeric_limits<size_t>::max() — end note |
h(u) | size_t | Изменять не буду u. |
Библиотека описывает стандартный набор требований allocators, которые представляют собой объекты типа класса, которые инкапсулируют информацию о модели распределения. Эта информация включает в себя сведения о типах указателей, типе их различия, типе размера объектов в этой модели распределения, а также о примитивах выделения и освобождения памяти для нее. Все перечисленные string types, containers (кроме массива), строковые буферы и строковые потоки (п [input.output]) и match_results параметризуются в терминах распределителей.
Шаблон класса allocator_traits предоставляет единый интерфейс для всех типов распределителей. В таблице 30 описаны типы, управляемые с помощью распределителей. В таблице 31 описаны требования к типам распределителя и, следовательно, к типам, используемым для создания экземпляров allocator_traits. Требование является необязательным, если последний столбец таблицы 31 указывает значение по умолчанию для данного выражения. В allocator_traits шаблоне стандартной библиотеки необязательное требование, которое не предоставляется распределителем, заменяется указанным выражением по умолчанию. Специализация пользователя allocator_traits может предоставлять различные значения по умолчанию и может предоставлять значения по умолчанию для требований, отличных от основного шаблона. В таблицах 30 и 31использование move и forward всегда относится к std::move и std::forward, соответственно.
Переменная | Определение |
T, U, C | любой - cvнеквалифицированный тип объекта ([basic.types]) |
X | класс Allocator для типа T |
Y | соответствующий класс Allocator для типа U |
XX | тип allocator_traits<X> |
YY | тип allocator_traits<Y> |
a, a1, a2 | lvalues типа X |
u | имя объявляемой переменной |
b | значение типа Y |
c | указатель типа, C* через который допустимо косвенное обращение |
p | значение типа XX::pointer, полученное при вызове a1.allocate, где a1 == a |
q | значение типа, XX::const_pointer полученное преобразованием из значения p. |
w | значение типа, XX::void_pointer полученное преобразованием из значения p |
x | значение типа, XX::const_void_pointer полученное преобразованием из значения q или значения w |
y | значение типа, XX::const_void_pointer полученное преобразованием из значения результата YY::allocate, или значение типа (возможно const) std::nullptr_t. |
n | значение типа XX::size_type. |
Args | пакет параметров шаблона |
args | пакет параметров функции с шаблоном Args&& |
Выражение | Тип возврата | Утверждение / примечание | Дефолт |
до / после состояния | |||
X::pointer | T* | ||
X::const_pointer | X::pointer конвертируется в X::const_pointer | pointer_traits<X::pointer>::rebind<const T> | |
X::void_pointer Y::void_pointer | X::pointer конвертируется в X::void_pointer. X::void_pointer и Y::void_pointer однотипны. | pointer_traits<X::pointer>::rebind<void> | |
X::const_void_pointer Y::const_void_pointer | X::pointer, X::const_pointerИ X::void_pointer могут быть конвертированы в X::const_void_pointer. X::const_void_pointer и Y::const_void_pointer однотипны. | pointer_traits<X::pointer>::rebind<const void> | |
X::value_type | Идентично T | ||
X::size_type | беззнаковый целочисленный тип | тип, который может представлять размер самого большого объекта в модели распределения. | make_unsigned_t<X::difference_type> |
X::difference_type | знаковый целочисленный тип | тип, который может представлять разницу между любыми двумя указателями в модели распределения. | pointer_traits<X::pointer>::difference_type |
typename X::template rebind<U>::other | Y | Для всех U (в том числе T) Y::template rebind<T>::other есть X. | См. Примечание A ниже. |
*p | T& | ||
*q | const T& | *q относится к тому же объекту, что и *p | |
p->m | тип T::m | Requires: (*p).m четко определено. эквивалентно (*p).m | |
q->m | тип T::m | Requires: (*q).m четко определено. эквивалентно (*q).m | |
static_cast<X::pointer>(w) | X::pointer | static_cast<X::pointer>(w) == p | |
static_cast<X::const_pointer>(x) | X::const_pointer | static_cast< X::const_pointer>(x) == q | |
pointer_traits<X::pointer>::pointer_to(r) | X::pointer | ||
a.allocate(n) | X::pointer | Память выделяется для n объектов типа, T но объекты не создаются. allocate может вызвать соответствующее исключение.175 [ Note: Если n == 0, возвращаемое значение не указано. ] — end note | |
a.allocate(n, y) | X::pointer | То же, что и a.allocate(n). Использование y не указано, но оно предназначено для помощи в местности. | a.allocate(n) |
a.deallocate(p,n) | (не используется) |
Requires: p должен быть значением, возвращенным более ранним вызовом allocate , который не был аннулирован промежуточным вызовом deallocate. n должен соответствовать значению, переданному allocate для получения этой памяти. Throws: Ничего такого. | |
a.max_size() | X::size_type | наибольшее значение, которое может быть значимо передано в X::allocate() | numeric_limits<size_type>::max() / sizeof(value_type) |
a1 == a2 | bool | возвращается true только в том случае, если память, выделенная каждым из них, может быть освобождена через другую. operator== должен быть рефлексивным, симметричным и транзитивным и не должен выходить через исключение. | |
a1 != a2 | bool | такой же как !(a1 == a2) | |
a == b | bool | такой же как a == Y::rebind<T>::other(b) | |
a != b | bool | такой же как !(a == b) | |
X u(a); X u = a; |
Не должен выходить из-за исключения. Postconditions: u == a | ||
X u(b); |
Не должен выходить из-за исключения. Postconditions: Y(u) == b, u == X(b) | ||
X u(std::move(a)); X u = std::move(a); |
Не должен выходить из-за исключения. Postconditions: u равно предыдущему значению a. | ||
X u(std::move(b)); |
Не должен выходить из-за исключения. Postconditions: u равно предыдущему значению X(b). | ||
a.construct(c, args) | (не используется) | Effects: Создает объект типа C в c | ::new ((void*)c) C(forward<Args>(args)...) |
a.destroy(c) | (не используется) | Effects: Уничтожает объект на c | c->~C() |
a.select_on_container_copy_construction() | X | Обычно возвращает либо, a либо X() | return a; |
X::propagate_on_container_copy_assignment | Идентичен или производный от true_type или false_type | true_type только если распределитель типа X должен быть скопирован, когда клиентскому контейнеру назначено копирование. См. Примечание B ниже. | false_type |
X::propagate_on_container_move_assignment | Идентичен или производный от true_type или false_type | true_type только в том случае, если распределитель типа X должен быть перемещен при назначении перемещения клиентскому контейнеру. См. Примечание B ниже. | false_type |
X::propagate_on_- container_swap | Идентичен или производный от true_type или false_type | true_type только если распределитель типа X должен быть заменен при замене клиентского контейнера. См. Примечание B ниже. | false_type |
X::is_always_equal | Идентичен или производный от true_type или false_type | true_type только тогда , когда выражение a1 == a2 гарантированно будет true для любых двух (возможно const) значений a1, a2 типа X. | is_empty<X>::type |
Примечание A. Шаблон класса-члена rebind в приведенной выше таблице фактически является шаблоном typedef. [ Note: В общем, если имя Allocator привязано к SomeAllocator<T>, то Allocator::rebind<U>::other имеет тот же тип, что и SomeAllocator<U>, где SomeAllocator<T>::value_type есть T и SomeAllocator<U>::value_type есть U. ] Если является экземпляром шаблона класса формы , где ноль или более аргументов типа и не предоставляет шаблон элемента, стандартный шаблон используется вместо него по умолчанию. Для типов распределителей, которые не являются экземплярами шаблонов приведенной выше формы, значение по умолчанию не предоставляется. — end note Allocator SomeAllocator<T, Args> Args Allocator rebind allocator_traits SomeAllocator<U, Args> Allocator::rebind<U>::other
Примечание B: Если X::propagate_on_container_copy_assignment::value есть true, X должно удовлетворять CopyAssignable requirements и операция копирования не должна вызывать исключений. Если X::propagate_on_container_move_assignment::value есть true, X должно удовлетворять, MoveAssignable requirements и операция перемещения не должна вызывать исключений. Если X::propagate_on_container_swap::value есть true, lvalues типа X должны быть, swappable и swap операция не должна вызывать исключений.
Тип распределителя X должен удовлетворять требованиям CopyConstructible. X::pointer, X::const_pointer, X::void_pointer, И X::const_void_pointer типы должны удовлетворять требования NullablePointer. Никакой конструктор, функция сравнения, операция копирования, операция перемещения или операция обмена для этих типов указателей не должны завершаться через исключение. X::pointer а X::const_pointer также должны удовлетворять требованиям а random access iterator и а contiguous iterator.
Пусть x1 и x2 обозначают объекты (возможно , различные) типов X::void_pointer, X::const_void_pointer, X::pointerили X::const_pointer. Тогда x1 и x2 являются equivalently-valued значениями указателей, если и только если оба x1 и x2 могут быть явно преобразованы в два соответствующих объекта px1 и px2 типа X::const_pointerс использованием последовательности static_casts, использующей только эти четыре типа, и выражение px1 == px2 оценивается как true.
Пусть w1 и w2 обозначают объекты типа X::void_pointer. Тогда для выражений
w1 == w2 w1 != w2
один или оба объекта могут быть заменены объектом типаX::const_void_pointer с эквивалентным значением без изменения семантики.
Пусть p1 и p2 обозначают объекты типа X::pointer. Тогда для выражений
p1 == p2 p1 != p2 p1 < p2 p1 <= p2 p1 >= p2 p1 > p2 p1 - p2
один или оба объекта могут быть заменены объектом типаX::const_pointer с эквивалентным значением без изменения семантики.
Распределитель может ограничивать типы, для которых он может быть создан, и аргументы, для которых он construct или его destroy члены могут вызываться. Если тип не может использоваться с конкретным распределителем, класс распределителя или вызов construct или destroy могут не создать экземпляра.
[ Example: Ниже приведен шаблон класса распределителя, поддерживающий минимальный интерфейс, удовлетворяющий требованиям таблицы 31:
template <class Tp>
struct SimpleAllocator {
typedef Tp value_type;
SimpleAllocator(ctor args);
template <class T> SimpleAllocator(const SimpleAllocator<T>& other);
Tp* allocate(std::size_t n);
void deallocate(Tp* p, std::size_t n);
};
template <class T, class U>
bool operator==(const SimpleAllocator<T>&, const SimpleAllocator<U>&);
template <class T, class U>
bool operator!=(const SimpleAllocator<T>&, const SimpleAllocator<U>&);
— end example ]
Если выравнивание, связанное с конкретным сверхвыровненным типом, не поддерживается распределителем, создание экземпляра распределителя для этого типа может завершиться ошибкой. Распределитель также может молча игнорировать запрошенное выравнивание. [ Note: Кроме того, функция-член allocate для этого типа может завершиться ошибкой, выбрасывая объект типа bad_alloc. ] — end note
Предполагается, что это a.allocate будет эффективное средство выделения одного объекта типа T, даже если sizeof(T) он невелик. То есть контейнеру не нужно поддерживать свой собственный список свободных мест.
Если X это класс распределителя для типа T, X дополнительно удовлетворяет требованиям полноты распределителя, если, T является ли тип полным или нет :
X это полный тип, и
все типы членов, allocator_traits<X> кроме value_type полных.
В этом разделе описаны ограничения для программ C ++, использующих возможности стандартной библиотеки C ++. Следующие подпункты определяют ограничения на использование программой namespaces, ее использование различных reserved names, ее использование headers, ее использование стандартных библиотечных классов в качестве базовых классов ([derived.classes]), ее определения replacement functionsи ее установку handler functions во время выполнения.
Поведение программы C ++ не определено, если она добавляет объявления или определения в пространство имен std или в пространство имен в пространстве имен, std если не указано иное. Программа может добавить специализацию шаблона для любого шаблона стандартной библиотеки в пространство имен std только в том случае, если объявление зависит от определяемого пользователем типа, а специализация соответствует требованиям стандартной библиотеки для исходного шаблона и не запрещена явно.176
Поведение программы на C ++ не определено, если она объявляет
явная специализация любой функции-члена шаблона класса стандартной библиотеки, или
явная специализация любого шаблона функции-члена стандартного библиотечного класса или шаблона класса, или
явная или частичная специализация любого шаблона класса-члена стандартного библиотечного класса или шаблона класса, или
руководство по вычету для любого стандартного шаблона класса библиотеки.
Программа может явно создать экземпляр шаблона, определенного в стандартной библиотеке, только в том случае, если объявление зависит от имени определяемого пользователем типа и создание экземпляра соответствует требованиям стандартной библиотеки для исходного шаблона.
Единица трансляции не должна объявлять пространство имен std как встроенное пространство имен ([namespace.def]).
Любой библиотечный код, который создает экземпляры других библиотечных шаблонов, должен быть подготовлен для адекватной работы с любой специализацией, задаваемой пользователем, которая соответствует минимальным требованиям настоящего международного стандарта.
Пространства имен верхнего уровня с именем, начинающимся с std непустой последовательности цифр и за которым следует непустая последовательность цифр, зарезервированы для будущей стандартизации. Поведение программы C ++ не определено, если она добавляет объявления или определения в такое пространство имен. [ Example: Пространство имен верхнего уровня std2 зарезервировано для использования в будущих версиях настоящего стандарта. ] — end example
Стандартная библиотека C ++ резервирует следующие типы имен:
макросы
глобальные имена
имена с внешней связью
Если программа объявляет или определяет имя в контексте, в котором оно зарезервировано, кроме случаев, явно разрешенных этим пунктом, ее поведение не определено.
В пространстве имен stdследующие имена зарезервированы для предыдущей стандартизации:
Единица трансляции, которая включает заголовок стандартной библиотеки, не должна#define или не #undef объявляется в каком-либо заголовке стандартной библиотеки.
Единица перевода не должна #define или не должна быть #undef лексически идентична ключевым словам, идентификаторам, перечисленным в Таблице 4, или attribute-tokens описанным в [dcl.attr].
Каждое имя, объявленное как объект с внешней связью в заголовке, зарезервировано для реализации, чтобы обозначить этот объект библиотеки с внешней связью 177 как в пространстве имен, так std и в глобальном пространстве имен.
Каждая глобальная сигнатура функции, объявленная с внешней связью в заголовке, зарезервирована для реализации, чтобы обозначить эту сигнатуру функции с внешней связью.178
Каждое имя из стандартной библиотеки C, объявленное с внешней связью , зарезервировано для реализации для использования в качестве имени со связью как в пространстве имен, так и в глобальном пространстве имен.extern "C" std
Каждая сигнатура функции из стандартной библиотеки C, объявленной с внешней связью, зарезервирована для реализации для использования в качестве сигнатуры функции с обоими extern "C" и extern "C++" связью179 или как имя области пространства имен в глобальном пространстве имен.
Список таких зарезервированных сигнатур функций с внешней связью включает setjmp(jmp_buf), объявленные или определенные в , и , объявленные или определенные в .<csetjmp>va_end(va_list)<cstdarg>
Для каждого типа T из стандартной библиотеки C180 типы ::T и std::T зарезервированы для реализации и, если они определены, ::T должны быть идентичны std::T.
Эти типы clock_t, div_t, FILE, fpos_t, lconv, ldiv_t, mbstate_t, ptrdiff_t, sig_atomic_t, size_t, time_t, tm, va_list, wctrans_t, wctype_t, и wint_t.
Literal suffix identifiers которые не начинаются с подчеркивания, зарезервированы для будущей стандартизации.
Сигнатуры виртуальных функций-членов, определенные для базового класса в стандартной библиотеке C ++, могут быть переопределены в производном классе, определенном в программе ( ).[class.virtual]
Пункты [language.support] до [thread] и Приложение [depr] описывают поведение множества функций, определенных стандартной библиотекой C ++. Однако при некоторых обстоятельствах некоторые из этих описаний функций также применимы к функциям замены, определенным в программе ([definitions]).
Программа на C ++ может предоставить определение для любой из следующих сигнатур функции распределения динамической памяти, объявленных в header <new> ([basic.stc.dynamic], [support.dynamic]):
operator new(std::size_t) operator new(std::size_t, std::align_val_t) operator new(std::size_t, const std::nothrow_t&) operator new(std::size_t, std::align_val_t, const std::nothrow_t&)
operator delete(void*) operator delete(void*, std::size_t) operator delete(void*, std::align_val_t) operator delete(void*, std::size_t, std::align_val_t) operator delete(void*, const std::nothrow_t&) operator delete(void*, std::align_val_t, const std::nothrow_t&)
operator new[](std::size_t) operator new[](std::size_t, std::align_val_t) operator new[](std::size_t, const std::nothrow_t&) operator new[](std::size_t, std::align_val_t, const std::nothrow_t&)
operator delete[](void*) operator delete[](void*, std::size_t) operator delete[](void*, std::align_val_t) operator delete[](void*, std::size_t, std::align_val_t) operator delete[](void*, const std::nothrow_t&) operator delete[](void*, std::align_val_t, const std::nothrow_t&)
Определения программы используются вместо версий по умолчанию, предоставляемых реализацией ([support.dynamic]). Такая замена происходит до запуска программы ([basic.def.odr], [basic.start]). Объявления программы не должны указываться как inline. Диагностика не требуется.
Стандартная библиотека C ++ предоставляет версию по умолчанию для следующей функции-обработчика (пункт [language.support]):
Программа на C ++ может устанавливать различные функции-обработчики во время выполнения, предоставляя указатель на функцию, определенную в программе или библиотеке, в качестве аргумента для (соответственно):
См. Также подпункты [alloc.errors]Ошибки выделения памяти и [support.exception]Обработка исключений.
Программа на C ++ может получить указатель на текущую функцию-обработчик, вызвав следующие функции:
В некоторых случаях (функции замены, функции обработчика, операции с типами, используемыми для создания экземпляров компонентов шаблона стандартной библиотеки) стандартная библиотека C ++ зависит от компонентов, предоставляемых программой C ++. Если эти компоненты не соответствуют их требованиям, настоящий международный стандарт не предъявляет требований к реализации.
В частности, эффекты не определены в следующих случаях:
for replacement functions, если установленная функция замены не реализует семантику применимого Required behavior: абзаца.
для функций-обработчиков ([new.handler], [terminate.handler]), если установленная функция-обработчик не реализует семантику соответствующего Required behavior: абзаца
для типов , используемых в качестве аргументов шаблона при создании экземпляра шаблона компонента, если операции по типу не реализуют семантику применимых требований подпункта ([allocator.requirements], [container.requirements], [iterator.requirements], [algorithms.requirements], [numeric.requirements]). Операции с такими типами могут сообщать об ошибке, вызывая исключение, если не указано иное.
если какая-либо функция замены, функция обработчика или операция деструктора завершается через исключение, если иное не разрешено в соответствующем Required behavior: абзаце.
если incomplete type используется в качестве аргумента шаблона при создании экземпляра компонента шаблона, если это специально не разрешено для этого компонента.
Каждое из следующих действий применяется ко всем аргументам функций, определенных в стандартной библиотеке C ++, если явно не указано иное.
Если аргумент функции имеет недопустимое значение (например, значение вне домена функции или указатель, недопустимый для предполагаемого использования), поведение не определено.
Если аргумент функции описывается как массив, указатель, фактически переданный функции, должен иметь такое значение, чтобы все вычисления адресов и доступ к объектам (это было бы действительным, если бы указатель действительно указывал на первый элемент такого массива) на самом деле действительны.
Если аргумент функции привязывается к параметру ссылки rvalue, реализация может предположить, что этот параметр является уникальной ссылкой на этот аргумент. [ Note: Если параметр является универсальным параметром формы T&& иA привязано lvalue типа , аргумент привязывается к ссылке lvalue ([temp.deduct.call]) и, таким образом, не охвачен предыдущим предложением. ] [ Если программа преобразует lvalue в xvalue, передавая это lvalue библиотечной функции (например, вызывая функцию с аргументом ), программа фактически просит эту функцию рассматривать это lvalue как временное. Реализация позволяет оптимизировать проверки наложения псевдонимов, которые могут потребоваться, если аргумент был lvalue. ] — end note Note: std::move(x) — end note
Поведение программы не определено, если вызовы стандартных библиотечных функций из разных потоков могут вызвать гонку данных. Условия, при которых это может произойти, указаны в [res.on.data.races]. [ Note: Изменение объекта стандартного типа библиотеки, который совместно используется потоками, рискует неопределенным поведением, если только объекты этого типа явно не указаны как доступные для совместного использования без гонок данных или пользователь не предоставит механизм блокировки. ] — end note
Если осуществляется доступ к объекту стандартного библиотечного типа, и начало объекта lifetime не происходит до доступа или доступ не происходит до конца времени существования объекта, поведение не определено, если не указано иное. [ Note: Это применимо даже к таким объектам, как мьютексы, предназначенным для синхронизации потоков. ] — end note
Использование заголовков в реализации обсуждается в [res.on.headers]: использование макросов в [res.on.macro.definitions], функций, не являющихся членами, функций- [global.functions]членов в [member.functions], предотвращения гонки данных в [res.on.data.races], спецификаторов доступа в [protection.within.classes], производного класса в [derivation]и исключений в [res.on.exception.handling].
Заголовок C ++ может включать другие заголовки C ++. Заголовок C ++ должен содержать объявления и определения, которые появляются в его синопсисе. Заголовок C ++, показанный в его синопсисе как включающий другие заголовки C ++, должен содержать объявления и определения, которые появляются в резюме этих других заголовков.
Некоторые типы и макросы определены более чем в одном заголовке. Каждый такой объект должен быть определен таким образом, чтобы любой заголовок, который его определяет, мог быть включен после любого другого заголовка, который также его определяет ([basic.def.odr]).
Они C standard library headers должны включать только соответствующий заголовок стандартной библиотеки C ++, как описано в [headers].
Не указано, определены ли какие-либо функции, не являющиеся членами, в стандартной библиотеке C ++ как inline.
Вызов сигнатуры функции, не являющейся членом, описанной в разделах [language.support] по [thread] и в приложении, [depr] должен вести себя так, как если бы реализация не объявила никаких дополнительных сигнатур функций, не являющихся членами.181
Реализация не должна объявлять сигнатуру функции, не являющейся членом, с дополнительными аргументами по умолчанию.
Если не указано иное, вызовы, выполняемые функциями в стандартной библиотеке для неоператорных функций, не являющихся членами, не используют функции из другого пространства имен, которые можно найти с помощью argument-dependent name lookup ([basic.lookup.argdep]). [ Note: Фраза «если не указано иное» применяется к таким случаям, как замена с требованиями ([swappable.requirements]). Исключение для перегруженных операторов разрешает поиск в зависимости от аргументов в следующих случаях ostream_iterator::operator=:
Effects:
*out_stream << value; if (delim != 0) *out_stream << delim; return *this;
— end note ]
Допустимая программа на C ++ всегда вызывает ожидаемую библиотечную функцию, не являющуюся членом. Реализация также может определять дополнительные функции, не являющиеся членами, которые в противном случае не вызывались бы действительной программой C ++.
Для невиртуальной функции-члена, описанной в стандартной библиотеке C ++, реализация может объявить другой набор сигнатур функций-членов при условии, что любой вызов функции-члена, который выберет перегрузку из набора объявлений, описанных в этом международном стандарте, ведет себя как если бы была выбрана эта перегрузка. [ Note: Например, реализация может добавлять параметры со значениями по умолчанию или заменять функцию-член с аргументами по умолчанию двумя или более функциями-членами с эквивалентным поведением или добавлять дополнительные подписи для имени функции-члена. ] — end note
Этот международный стандарт явно требует, чтобы определенные стандартные библиотечные функции были constexpr. Реализация не должна объявлять какую-либо сигнатуру стандартной библиотечной функции, constexpr за исключением тех, где это явно требуется. В любом заголовке, который предоставляет любые не определяющие объявления функций или конструкторов constexpr, реализация должна предоставлять соответствующие определения.
Когда в требованиях к алгоритму указано, что он «стабилен» без дальнейшей разработки, это означает:
Для sort алгоритмов сохраняется относительный порядок эквивалентных элементов.
Для алгоритмов remove и copy сохраняется относительный порядок элементов, которые не удаляются.
Для merge алгоритмов для эквивалентных элементов в исходных двух диапазонах элементы из первого диапазона (с сохранением их исходного порядка) предшествуют элементам из второго диапазона (с сохранением их исходного порядка).
В этом разделе указаны требования, которым должны соответствовать реализации для предотвращения data races. Каждая стандартная библиотечная функция должна соответствовать каждому требованию, если не указано иное. Реализации могут предотвратить гонку данных в случаях, отличных от указанных ниже.
Функция стандартной библиотеки C ++ не должна прямо или косвенно обращаться к объектам ([intro.multithread]), доступным потокам, отличным от текущего потока, если к объектам не осуществляется прямой или косвенный доступ через аргументы функции, в том числе this.
Функция стандартной библиотеки C ++ не должна прямо или косвенно изменять объекты ([intro.multithread]), доступные потокам, отличным от текущего потока, если к объектам не осуществляется прямой или косвенный доступ через неконстантные аргументы функции, включая this.
[ Note: Это означает, например, что реализации не могут использовать статический объект для внутренних целей без синхронизации, потому что это может вызвать гонку данных даже в программах, которые явно не разделяют объекты между потоками. ] — end note
Функция стандартной библиотеки C ++ не должна обращаться к объектам, косвенно доступным через ее аргументы или через элементы аргументов контейнера, кроме как путем вызова функций, требуемых ее спецификацией, для этих элементов контейнера.
Операции с итераторами, полученные путем вызова контейнера стандартной библиотеки или строковой функции-члена, могут обращаться к базовому контейнеру, но не должны его изменять. [ Note: В частности, операции контейнера, которые делают итераторы недействительными, конфликтуют с операциями над итераторами, связанными с этим контейнером. ] — end note
Реализации могут совместно использовать свои внутренние объекты между потоками, если объекты не видны пользователям и защищены от скачков данных.
Если не указано иное, функции стандартной библиотеки C ++ должны выполнять все операции исключительно в текущем потоке, если эти операции оказывают влияние visible на пользователей.
Не указано, является ли какая-либо сигнатура функции или класс, описанные в Разделах [language.support] по [thread] и Приложение [depr] , к friend другому классу в стандартной библиотеке C ++.
Реализация может наследовать любой класс в стандартной библиотеке C ++ от класса с именем, зарезервированным для реализации.
Некоторые классы, определенные в стандартной библиотеке C ++, должны быть производными от других классов стандартной библиотеки C ++. Реализация может получить такой класс непосредственно из требуемой базы или косвенно через иерархию базовых классов с именами, зарезервированными для реализации.
В любом слючае:
Каждый базовый класс, описанный как, virtual должен быть виртуальным;
Каждый базовый класс, не указанный как virtual , не должен быть виртуальным;
Если явно не указано иное, типы с разными именами должны быть разными типами.182
Все типы, указанные в стандартной библиотеке C ++, не должны бытьfinal типами, если не указано иное.
Любая из функций, определенных в стандартной библиотеке C ++, может сообщать о сбое, генерируя исключение типа, описанного в его Throws: абзаце, или типа, производного от типа, названного в Throws: абзаце, которое будет перехвачено обработчиком исключений для базового типа. .
Функции из стандартной библиотеки C не должны вызывать исключения, 183 за исключением случаев, когда такая функция вызывает программную функцию, которая вызывает исключение.184
Операции деструктора, определенные в стандартной библиотеке C ++, не должны вызывать исключений. Каждый деструктор в стандартной библиотеке C ++ должен вести себя так, как если бы он имел спецификацию исключения, не вызывающего выброса.
Функции, определенные в стандартной библиотеке C ++, которые не имеют Throws: абзаца, но имеют спецификацию потенциально вызывающего исключения, могут вызывать исключения, определяемые реализацией.185 Реализации должны сообщать об ошибках, бросая исключения из или полученных из стандартных классов исключений ([bad.alloc], [support.exception], [std.exceptions]).
Реализация может усилить спецификацию исключения для невиртуальной функции, добавив спецификацию исключения исключения.
То есть все функции библиотеки C можно рассматривать так, как если бы они были отмечены noexcept. Это позволяет реализациям оптимизировать производительность на основе отсутствия исключений во время выполнения.
Функции qsort() и bsearch() ([alg.c.library]) удовлетворяют этому условию.
В частности, они могут сообщить об ошибке выделения хранилища, выбрасывая исключение типа bad_allocили класса, производного от bad_alloc.
Объекты, созданные стандартной библиотекой, которые могут содержать значение указателя, предоставленное пользователем или целое число типа, std::intptr_t должны хранить такие значения в файле traceable pointer location. [ Note: Другим библиотекам настоятельно рекомендуется делать то же самое, поскольку невыполнение этого может привести к случайному использованию указателей, которые не выводятся безопасно. Библиотеки, хранящие указатели вне адресного пространства пользователя, должны создавать впечатление, что они хранятся и извлекаются из отслеживаемого местоположения указателя. ] — end note
Некоторые функции стандартной библиотеки C ++ сообщают об ошибках через std::error_code объект.category() Член этого объекта должен возвращать std::system_category() для ошибок, происходящих из операционной системы, или ссылку на объект, определенный реализацией, error_category для ошибок, возникающих в другом месте. Реализация должна определять возможные значения value() для каждой из этих категорий ошибок. [ Example: Для операционных систем, основанных на POSIX, реализациям рекомендуется определять std::system_category() значения как идентичные errno значениям POSIX , с дополнительными значениями, как определено в документации операционной системы. Реализациям для операционных систем, не основанных на POSIX, рекомендуется определять значения, идентичные значениям операционной системы. Для ошибок, которые происходят не из операционной системы, реализация может предоставить перечисления для связанных значений. ] — end example
Объекты типов, определенных в стандартной библиотеке C ++, можно перемещать из ([class.copy]). Операции перемещения могут быть заданы явно или неявно. Если не указано иное, такие перемещенные объекты должны быть переведены в допустимое, но неуказанное состояние.