此頁面中列出的具名要求,是 C++ 標準的規(guī)范性文本中使用的具名要求,用于定義標準庫的期待。
某些具名要求在 C++20 中正在以概念語言特性進行形式化。在那之前,確保以滿足這些要求的模板實參實例化標準庫模板是程序員的重擔。若不這么做,則可能導(dǎo)致非常復(fù)雜的編譯器診斷。
全庫范圍的概念
包含分配信息的類類型
封裝訪問/尋址,分配/解分配,以及對象的構(gòu)造/析構(gòu)的策略。
可能需要分配或釋放內(nèi)存的每個標準庫組件,從 std::string
、std::vector
和 std::array
以外的所有容器,到 std::shared_ptr
和 std::function
,都通過 Allocator分配器 進行這些操作:分配器是滿足下列要求的類類型對象。
某些要求是可選的:模板 std::allocator_traits 為所有可選要求提供默認實現(xiàn),且所有標準庫容器和其他具分配器類,都是通過 std::allocator_traits
訪問分配器,而并不直接訪問。
要求
給定
- 無 cv 限定的對象類型
T
- 針對類型
T
的分配器 (Allocator) 類型A
-
A
類型的對象a
-
B
,為針對某個無 cv 限定的對象類型U
的對應(yīng)分配器 (Allocator) 類型(重綁定A
所得) -
B
類型的對象b
-
allocator_traits<A>::pointer
類型的值ptr
,由調(diào)用 allocator_traits<A>::allocate() 所獲得 -
allocator_traits<A>::const_pointer
類型的值cptr
,從ptr
轉(zhuǎn)換而獲得 -
allocator_traits<A>::void_pointer
類型的值vptr
,從ptr
轉(zhuǎn)換而獲得 -
allocator_traits<A>::const_void_pointer
類型的值cvptr
,從cptr
或vptr
轉(zhuǎn)換而獲得 -
xptr
,為針對某各無 cv 限定對象類型X
的可解引用指針 -
r
,為從表達式 *ptr 獲得的T
類型的左值 -
allocator_traits<A>::size_type
類型的值n
表達式 | 要求 | 返回類型 |
---|---|---|
A::pointer (可選) | 滿足可空指針 (NullablePointer) 、遺留隨機訪問迭代器 (LegacyRandomAccessIterator) 及遺留連續(xù)迭代器 (LegacyContiguousIterator) (見下文綴飾指針) | |
A::const_pointer (可選) |
A::pointer 可轉(zhuǎn)換為 A::const_pointer 。可空指針 (NullablePointer) 、遺留隨機訪問迭代器 (LegacyRandomAccessIterator) 及遺留連續(xù)迭代器 (LegacyContiguousIterator) |
|
A::void_pointer (可選) |
A::pointer 可轉(zhuǎn)換為 A::void_pointer
|
|
A::const_void_pointer (可選) |
A::pointer 、A::const_pointer 及 A::void_pointer 可轉(zhuǎn)換到 A::const_void_pointer
|
|
A::value_type | 類型 T
|
|
A::size_type (可選) |
A::size_type 能表示 A 所能分配的最大對象的大小 |
無符號整數(shù)類型 |
A::difference_type (可選) |
A::difference_type 能表示任意兩個指向 A 所分配對象的指針之間的差 |
有符號整數(shù)類型 |
A::template rebind<U>::other (可選)[1] | 對于任何 U ,B::template rebind<T>::other 為 A
|
類型 B
|
*ptr | T& |
|
*cptr | *cptr 與 *ptr 標識同一對象 | const T& |
ptr->m | 若 (*ptr).m 良構(gòu),則與 (*ptr).m 相同 |
T::m 的類型 |
cptr->m | 若 (*cptr).m 良構(gòu),則與 (*cptr).m 相同 |
T::m 的類型 |
static_cast<A::pointer>(vptr) | static_cast<A::pointer>(vptr) == ptr | A::pointer |
static_cast<A::const_pointer>(cvptr) | static_cast<A::const_pointer>(cvptr) == cptr | A::const_pointer |
std::pointer_traits<A::pointer>::pointer_to(r) | A::pointer |
|
a.allocate(n) | 分配適合 n 個 T 類型對象的存儲,但不構(gòu)造它們??梢話伄惓!?/td>
| A::pointer |
a.allocate(n, cvptr) (可選) | 與 a.allocate(n) 相同,但可以以未指明的方式使用 cvptr (從 a.allocate() 獲得的指針或 nullptr_t )以協(xié)助局部性 |
A::pointer |
a.deallocate(ptr, n) | 解分配 ptr 所指向的存儲,該指針必須是先前從對 allocate 的調(diào)用獲得的指針,且未因中間對 deallocate 的調(diào)用而失效。n 必須匹配先前傳遞給 allocate 的值。不拋異常。 |
(不使用) |
a.max_size() (可選) | 能傳遞給 A::allocate() 的最大值 |
A::size_type |
a1 == a2 | 僅若分配器 a1 分配的存儲能通過 a2 解分配才返回 true。建立自反、對稱和可傳遞關(guān)系。不拋異常。 |
bool |
a1 != a2 | 與 !(a1==a2) 相同 | bool |
A a1(a) A a1 = a |
復(fù)制構(gòu)造 a1 以滿足 a1 == a。不拋異常。(注意:所有分配器 (Allocator) 也都滿足可復(fù)制構(gòu)造 (CopyConstructible) ) |
|
A a(b) | 構(gòu)造滿足 B(a)==b 和 A(b)==a 的 a 。不拋異常。(注意,這意味著所有因 rebind 相關(guān)聯(lián)的分配器都彼此維護資源,例如內(nèi)存池) |
|
A a1(std::move(a)) A a1 = std::move(a) |
構(gòu)造 a1 使之等于 a 之前的值。不拋異常。 a 的值不變且 a1 == a。 (C++17 起) |
|
A a(std::move(b)) | 構(gòu)造 a 使之等于 A(b) 之前的值。不拋異常。 |
|
a.construct(xptr, args) (可選) | 在先前分配的存儲中由 xptr 所指向的地址上,以 args 為構(gòu)造函數(shù)實參構(gòu)造一個 X 類型的對象 |
|
a.destroy(xptr) (可選) | 析構(gòu) xptr 所指向的 X 類型的對象,但不解分配任何存儲。 |
|
a.select_on_container_copy_construction() (可選) | 提供一個 A 實例,以被從當前正使用 a 的容器所復(fù)制構(gòu)造的容器使用。通常要么返回 a 的副本,要么為默認構(gòu)造的 A() 。 |
A |
A::propagate_on_container_copy_assignment (可選) | 若在使用 A 類型的分配器的容器被復(fù)制賦值時需要復(fù)制該分配器,則為 true。注意,若源和目標容器的分配器比較不相等,則復(fù)制賦值時必須用舊分配器解分配目標的內(nèi)存,再在進行各元素(和分配器)的復(fù)制之前用新分配器分配內(nèi)存 |
std::true_type 或 std::false_type 或從它派生的類型 |
A::propagate_on_container_move_assignment (可選) | 若在使用 A 類型的分配器的容器被移動賦值時需要移動該分配器,則為 true。若此成員是 false 且源和目標容器的分配器比較不相等,則移動賦值不能奪取源內(nèi)存的所有權(quán),而必須逐個進行元素的移動賦值或移動構(gòu)造,按需調(diào)整其自身內(nèi)存的大小。 |
std::true_type 或 std::false_type 或從它派生的類型 |
A::propagate_on_container_swap (可選) | 若在使用 A 類型的分配器的兩個容器進行交換時需要交換分配器,則為 true。若此成員是 false 且兩個容器的分配器比較不相等,則容器交換的行為未定義。 |
std::true_type 或 std::false_type 或從它派生的類型 |
A::is_always_equal (C++17 起) (可選) | 若兩個 A 類型的分配器始終比較相等則為 true。若不提供,則 std::allocator_traits 默認它等于 std::is_empty<A>::type |
std::true_type 或 std::false_type 或從它派生的類型 |
注:
- ↑ 僅當此分配器是 SomeAllocator<T, Args> 形式的模板(其中
Args
是零或更多額外的模板類型形參)時,rebind 才是可選的(由 std::allocator_traits 提供)。
另外,為使類型
|
(C++17 起) |
給定
則,當且僅當 給定
則對于表達式 w1 == w2 與 w1 != w2,任一或兩個對象都可由值等價的 給定
則,對于表達式 p1 == p2、p1 != p2、p1 < p2、p1 <= p2、p1 >= p2、p1 > p2、p1 - p2},任一或兩個對象都可由值等價的 上述要求使得比較容器 (Container) 的 iterator 和 const_iterator 成為可能。 |
(C++14 起) |
分配器完整性要求若無論
|
(C++17 起) |
綴飾指針
當成員類型 pointer
不是原生指針時,它通常被稱為“綴飾指針(fancy pointer)”。這種指針曾為支持分段內(nèi)存架構(gòu)而引入,并在當今用于訪問在某些不同于原生指針所訪問的同質(zhì)虛擬地址空間的地址空間中所分配的對象。綴飾指針的一個實例是映射的不依賴地址指針 boost::interprocess::offset_ptr,它使得在共享內(nèi)存和在每個進程中映射到不同地址的映射到內(nèi)存文件中,分配 std::set 一類的基于結(jié)點的數(shù)據(jù)結(jié)構(gòu)可行。通過類模板 std::pointer_traits,綴飾指針可以獨立于提供它們的分配器而使用。
標準庫
下列標準庫組件滿足分配器 (Allocator) 要求:
allocator |
默認的分配器 (類模板) |
scoped_allocator_adaptor (C++11) |
為多級容器實現(xiàn)的多級分配器 (類模板) |
polymorphic_allocator (C++17)文章來源:http://www.zghlxwxcb.cn/news/detail-782866.html |
以 std::memory_resource 構(gòu)造,支持基于它的運行時多態(tài)的分配器 (類模板) |
?文章來源地址http://www.zghlxwxcb.cn/news/detail-782866.html
到了這里,關(guān)于C++ 具名要求-全庫范圍的概念 -包含分配信息的類類型(Allocator)的文章就介紹完了。如果您還想了解更多內(nèi)容,請在右上角搜索TOY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!