Megjegyzés
Az oldalhoz való hozzáféréshez engedély szükséges. Megpróbálhat bejelentkezni vagy módosítani a címtárat.
Az oldalhoz való hozzáféréshez engedély szükséges. Megpróbálhatja módosítani a címtárat.
A Standard kódtár különböző típusbiztos tárolókat biztosít a kapcsolódó objektumok gyűjteményeinek tárolásához. A tárolók osztálysablonok. Tárolóváltozó deklarálásakor meg kell adnia a tároló által tárolni kívánt elemek típusát. A tárolók inicializáló listákkal hozhatók létre. Tagfüggvényekkel rendelkeznek az elemek hozzáadásához és eltávolításához, valamint más műveletek végrehajtásához.
Iterálja át a tároló elemeit, és iterátorokkal érheti el az egyes elemeket. Az iterátorokat kifejezetten használhatja tagfüggvények, operátorok és globális függvények használatával. Implicit módon is használhatja őket, például egy ciklustartomány használatával. Az összes C++ standard kódtár-tároló iterátorai közös felülettel rendelkeznek, de mindegyik tároló saját speciális iterátorokat határoz meg.
A tárolók három kategóriába sorolhatók: szekvenciatárolók, asszociatív tárolók és tárolóadapterek.
Szekvenciatárolók
A szekvenciatárolók megtartják a megadott beszúrt elemek sorrendjét.
A vector
tároló tömbként viselkedik, de szükség szerint automatikusan növekedhet. Véletlenszerű hozzáféréssel rendelkezik, és egybefüggően van tárolva, a hossz pedig rendkívül rugalmas. Ezen okokból és egyebek vector
miatt a legtöbb alkalmazás előnyben részesített szekvenciatárolója. Ha kétségei vannak abban, hogy milyen szekvenciatárolót használjon, először használjon vektort! További információ: vector
Osztály.
A array
tárolók erősségei vector
közül néhányat, de a hossz nem olyan rugalmas. További információ: array
Osztály.
A deque
(két végű üzenetsor) tároló gyors beszúrásokat és törléseket tesz lehetővé a tároló elején és végén. Megosztja a véletlenszerű hozzáférés és a rugalmas hossz előnyeit vector
, de nem egybefüggő. További információ: deque
Osztály.
A list
tárolók kétszeresen csatolt listák, amelyek lehetővé teszik a kétirányú hozzáférést, a gyors beszúrásokat és a gyors törléseket bárhol a tárolóban, de a tároló egy eleméhez nem férhet hozzá véletlenszerűen. További információ: list
Osztály.
A forward_list
tárolók egymáshoz kapcsolódó listák – a tárolók továbbítási hozzáférésű list
verziója. További információ: forward_list
Osztály.
Asszociatív tárolók
Az asszociatív tárolókban az elemek előre meghatározott sorrendbe vannak beszúrva– például növekvő sorrendben. A rendezetlen asszociatív tárolók is elérhetők. Az asszociatív tárolók két részhalmazba csoportosíthatók: térképek és készletek.
A map
más néven szótár egy kulcs-érték párból áll. A rendszer a kulcs használatával rendezi a sorozatot, és az érték hozzá van rendelve. Előfordulhat például, hogy olyan map
kulcsok találhatók, amelyek egy szöveg minden egyedi szavát jelölik, valamint a megfelelő értékeket, amelyek azt jelzik, hogy az egyes szavak hányszor jelennek meg a szövegben. A rendezetlen verzió az map
unordered_map
. További információ: map
Osztály és unordered_map
osztály.
Az A set
csak az egyedi elemek növekvő tárolója – az érték is a kulcs. A rendezetlen verzió az set
unordered_set
. További információ: set
Osztály és unordered_set
osztály.
Egyszerre map
csak set
egy kulcs vagy elem egy példányát szúrhatja be a tárolóba. Ha több elempéldányra van szükség, használja multimap
vagy multiset
. A rendezetlen verziók és unordered_multimap
a unordered_multiset
. További információ: multimap
Osztály, unordered_multimap
Osztály, multiset
Osztály és unordered_multiset
Osztály.
A rendezett térképek és -készletek támogatják a kétirányú iterátorokat, a rendezetlen megfelelőik pedig támogatják a továbbítási iterátorokat. További információ: Iterators.
Heterogén keresés asszociatív tárolókban (C++14)
A rendezett asszociatív tárolók (térkép, többtérkép, készlet és többhalmaz) mostantól támogatják a heterogén kereséseket, ami azt jelenti, hogy már nem kell pontosan ugyanazt az objektumtípust átadnia, mint a tagfüggvények kulcsának vagy elemének, például find()
és lower_bound()
. Ehelyett bármely olyan típust átadhat, amelyhez túlterhelt operator<
érték van definiálva, amely lehetővé teszi a kulcstípussal való összehasonlítást.
A heterogén keresés a tárolóváltozó deklarálásakor a "rombusz funktor" összehasonlító megadásakor std::less<>
std::greater<>
engedélyezve van, az itt látható módon:
std::set<BigObject, std::less<>> myNewSet;
Ha az alapértelmezett összehasonlítót használja, akkor a tároló pontosan ugyanúgy viselkedik, mint a C++11 és korábbi verziókban.
Az alábbi példa bemutatja, hogyan lehet túlterhelni operator<
, hogy a std::set
felhasználók egyszerűen elvégezhessék a kereséseket úgy, hogy egy kis sztringet adnak át, amely összehasonlítható az egyes objektumok tagjával BigObject::id
.
#include <set>
#include <string>
#include <iostream>
#include <functional>
using namespace std;
class BigObject
{
public:
string id;
explicit BigObject(const string& s) : id(s) {}
bool operator< (const BigObject& other) const
{
return this->id < other.id;
}
// Other members....
};
inline bool operator<(const string& otherId, const BigObject& obj)
{
return otherId < obj.id;
}
inline bool operator<(const BigObject& obj, const string& otherId)
{
return obj.id < otherId;
}
int main()
{
// Use C++14 brace-init syntax to invoke BigObject(string).
// The s suffix invokes string ctor. It is a C++14 user-defined
// literal defined in <string>
BigObject b1{ "42F"s };
BigObject b2{ "52F"s };
BigObject b3{ "62F"s };
set<BigObject, less<>> myNewSet; // C++14
myNewSet.insert(b1);
myNewSet.insert(b2);
myNewSet.insert(b3);
auto it = myNewSet.find(string("62F"));
if (it != myNewSet.end())
cout << "myNewSet element = " << it->id << endl;
else
cout << "element not found " << endl;
// Keep console open in debug mode:
cout << endl << "Press Enter to exit.";
string s;
getline(cin, s);
return 0;
}
//Output: myNewSet element = 62F
A következő tagfüggvények a térképen, a többtérképen, a készleten és a többhalmazon túlterheltek a heterogén keresés támogatásához:
talál
darabszám
lower_bound
upper_bound
equal_range
Tárolóadapterek
A tárolóadapterek olyan sorozatok vagy asszociatív tárolók változatai, amelyek az egyszerűség és az egyértelműség érdekében korlátozzák a felületet. A tárolóadapterek nem támogatják az iterátorokat.
A queue
tároló a FIFO (első be- és kifelé) szemantikáját követi. Az első leküldéses elem – vagyis az üzenetsorba beszúrva – az első, amelyet ki kell venni az üzenetsorból. További információ: queue
Osztály.
A priority_queue
tárolók úgy vannak rendszerezve, hogy a legmagasabb értékkel rendelkező elem mindig az első legyen az üzenetsorban. További információ: priority_queue
Osztály.
A stack
tároló a LIFO (utolsó be, első ki) szemantikáját követi. A veremen az utolsó leküldéses elem az első elem. További információ: stack
Osztály.
Mivel a tárolóadapterek nem támogatják az iterátorokat, nem használhatók a C++ standard kódtár algoritmusaival. További információ: Algoritmusok.
A tárolóelemekre vonatkozó követelmények
A C++ standard kódtár-tárolóba beszúrt elemek általában bármilyen típusúak lehetnek, ha másolhatók. A csak mozgatható elemek – például a vector<unique_ptr<T>>
használatukkal unique_ptr<>
létrehozott elemek mindaddig működnek, amíg nem hívja meg a másolásra kísérletet tevő tagfüggvényeket.
A destruktor nem hozhat kivételt.
A rendezett asszociatív tárolóknak – a jelen cikkben korábban ismertetett módon – nyilvános összehasonlító operátorral kell rendelkezniük. Alapértelmezés szerint az operátor az operator<
, de még azok a típusok is támogatottak, amelyek nem működnek operator<
.
A tárolók egyes műveleteihez szükség lehet egy nyilvános alapértelmezett konstruktorra és egy nyilvános egyenértékűségi operátorra is. A rendezetlen asszociatív tárolók például az egyenlőség és a kivonatolás támogatását igénylik.
Tárolóelemek elérése
A tárolók elemei iterátorokkal érhetők el. További információ: Iterators.
Megjegyzés:
A ciklusok tartományalapú használatával is iterálhat a C++ standard kódtár-gyűjteményeken.
Tárolók összehasonlítása
Minden tároló túlterheli az operátor== operátort két azonos típusú, azonos elemtípusú tároló összehasonlításához. A == használatával összehasonlíthat egy vektorsztringet egy másik vektorsztringgel<>, de nem használhatja vektorsztring<> és listasztring<> összehasonlítására, illetve vektorsztring<> és vektor<karakter*> összehasonlítására.<> A C++98/03 alkalmazásban használhatja std::equal
vagy std::mismatch
összehasonlíthatja az eltérő tárolótípusokat és/vagy elemtípusokat. A C++11-ben is használható std::is_permutation
. Ezekben az esetekben azonban a függvények feltételezik, hogy a tárolók hossza megegyezik. Ha a második tartomány rövidebb az elsőnél, akkor nem definiált viselkedési eredmények jelennek meg. Ha a második tartomány hosszabb, az eredmények továbbra is helytelenek lehetnek, mert az összehasonlítás soha nem folytatódik az első tartomány végéig.
Eltérő tárolók összehasonlítása (C++14)
A C++14-es és újabb verziókban összehasonlíthatja a különböző tárolók és/vagy eltérő elemek típusait a std::equal
két teljes tartományt tartalmazó , std::mismatch
vagy std::is_permutation
függvénytúlterhelések egyikével. Ezek a túlterhelések lehetővé teszik a tárolók különböző hosszúságú összehasonlítását. Ezek a túlterhelések sokkal kevésbé érzékenyek a felhasználói hibákra, és úgy vannak optimalizálva, hogy állandó időben hamis értéket adjanak vissza, amikor eltérő hosszúságú tárolókat hasonlítanak össze. Ezért javasoljuk, hogy használja ezeket a túlterheléseket, hacsak nincs egyértelmű oka arra, hogy ne, vagy olyan tárolót std::list
használ, amely nem élvezi a kéttartományos optimalizálás előnyeit.
Lásd még
Párhuzamos tárolók
<sample container>
Szálbiztonság a C++ Standard könyvtárban