Ich arbeite an einer Anwendung, in der ich einige STL-Container einsetzen möchte. Die Anwendung führt bestimmte Schritte aus, wenn der Speicherverbrauch einen Schwellenwert erreicht. Zu diesem Zweck muss eine genaue Berechnung durchgeführt werden, wie viel Speicherplatz STL-Container belegen.
%Vor%So schätze ich den Speicher:
Um die Größe von StringList
zu erreichen, überlappen Sie alle Elemente des Vektors und fügen Sie die String-Größen hinzu.
Fügen Sie dann endlich sizeof(StringList);
Wenn Sie die Größe von Mapstring überschreiten, führen Sie eine Schleife über alle Schlüssel des Containers aus, fügen Sie die Stringgrößen hinzu und fügen Sie dann die Größen von int hinzu, die mapstring.size()*sizeof(int)
ist. Dann füge endlich sizeof(mapstring);
Ich denke, ein besserer Ansatz bestünde darin, die eigene Zuweisungsklasse anzugeben und die Speicherbelegung zu verfolgen, aber das Schreiben einer solchen könnte nicht-trivial sein. Sieht diese Schätzung gut aus?
Für std::vector
und std::string
würde die Kapazität und nicht die Größe ausreichen
sei eine bessere Annäherung. Für knotenbasierte Container ( std::set
,
usw.), möchten Sie die Anzahl der Knoten (ungefähr die Anzahl der Knoten) multiplizieren
Elemente) mal die Größe jedes Knotens. Dies ist jedoch nur dann richtig, wenn
Der Zuordner verwendet keinen optimierten Poolzuordner für die Knoten.
Wenn Sie wirklich wissen möchten, wie viel Speicher verwendet wird, a
Eine bessere Strategie wäre es, die globalen operator new
und
operator delete
, und verfolgen Sie die tatsächlichen Zuordnungen. Sogar mehr
genau wäre es, malloc
und free
zu ersetzen. Formal ist das nicht
erlaubt, aber in der Praxis habe ich noch nie eine Implementierung wo gefunden
es funktioniert nicht. Auf der anderen Seite, wenn Sie malloc
und free
ersetzen,
Sie müssen die eigentliche Speicherverwaltung selbst implementieren. Wenn du
Ersetzen Sie operator new
und operator delete
, Sie können malloc
und verwenden
free
, was es ziemlich trivial macht.
Beachten Sie auch, dass jede Zuweisung einen festen Overhead hat. A 100000 Zuweisungen von je 10 Byte belegen deutlich mehr Speicher als 10 Zuweisungen von jeweils 100000 Bytes.
A std::vector<element>
benötigt normalerweise 3 Maschinenwörter insgesamt + sizeof (Element) * capacity()
des Speichers. Bei typischen Implementierungen besteht der Overhead aus Zeigern auf den Anfang, das Ende und die aktuelle Größe des Vektors. Die Elemente selbst sind in zusammenhängendem Speicher gespeichert. capacity()
hat normalerweise Platz für die doppelte Anzahl an Elementen.
A std::map<element, int>
benötigt normalerweise ungefähr 2 Maschinenwörter insgesamt + 3 Maschinenwörter pro Element + [sizeof (Element) + sizeof (int)] * num_elements des Speichers. Bei typischen Implementierungen besteht der Overhead aus Zeigern auf die gespeicherten Elemente. Die Elemente selbst werden in einem binären Baum mit Zeigern zu ihrem Eltern und zwei Kindern gespeichert.
Mit diesen Faustregeln müssen Sie nur die durchschnittliche Anzahl der Zeichen pro String und die Gesamtzahl der Strings kennen, um den Gesamtspeicherverbrauch zu kennen.
Tags und Links c++ stl map vector memory-management