Frage

In der Regel, was ist der beste Weg, binäre Daten in C ++ zu speichern? Die Optionen, soweit ich kann sagen, so ziemlich einkochen zu verwenden Strings oder vector s. (Ich werde die Möglichkeit, char * s und malloc () s weglassen, da ich speziell auf C ++ beziehen).

In der Regel habe ich nur einen String verwenden, aber ich bin nicht sicher, ob es Gemeinkosten ich fehle, oder Konvertierungen, die STL intern tut das könnte Chaos mit dem Verstand von binären Daten. Hat jemand irgendwelche Zeiger (har) auf das? Vorschläge oder Präferenzen eine oder andere Weise?

War es hilfreich?

Lösung

Vektor von char ist schön, weil der Speicher contiguious ist. Daher können Sie es mit einer Menge von C-API wie Berkley Sockets oder Datei-APIs verwenden. Sie können die folgenden tun, zum Beispiel:

  std::vector<char> vect;
  ...
  send(sock, &vect[0], vect.size());

und es wird funktionieren.

Sie können es im Wesentlichen behandeln wie jedes andere char-Puffer dynamisch zugewiesen. Sie können scannen nach oben und unten für magische Zahlen oder prasselt suchen. Sie können es teilweise an Ort und Stelle analysieren. Für von einem Socket empfangen kann man sehr leicht die Größe es mehr Daten anzuhängen.

Der Nachteil ist, Ändern der Größe ist nicht sehr effizient (oder die Größe vorbelegen umsichtig) und Streichung von der Vorderseite des Arrays wird auch sehr ineficient sein. Wenn Sie brauchen, um, sagen wir, pop nur ein oder zwei Zeichen zu einem Zeitpunkt vor der Front der Datenstruktur sehr häufig, das Kopieren auf eine deque vor dieser Verarbeitung kann eine Option sein. Das kostet Sie eine Kopie und deque Speicher ist nicht zusammenhängend, so kann man nicht nur einen Zeiger auf eine C-API übergeben.

Unterm Strich lernt die Datenstrukturen und ihre Vor- und Nachteile vor dem Tauchen in jedoch Vektor von char ist in der Regel, was ich in der allgemeinen Praxis gebraucht.

Andere Tipps

Das größte Problem mit std :: string ist, dass der aktuelle Standard garantiert nicht, dass die zugrunde liegenden Speicher angrenzt. Allerdings gibt es keine bekannten STL-Implementierungen, wo Zeichenfolge nicht zusammenhängend ist, so in der Praxis wird es wohl nicht scheitern. In der Tat ist der neue C ++ 0x-Standard, dieses Problem zu beheben, gehen, durch, dass std :: string Mandatierung verwendet einen zusammenhängenden Puffer, wie std :: vector.

Ein weiteres Argument gegen Zeichenfolge ist, dass der Name vermuten lässt, dass es eine Zeichenfolge enthält, kein Binärpuffer, die Verwirrung zu denen verursachen kann, die den Code zu lesen.

Das heißt, ich empfehlen Vektor als auch.

Ich benutze std::string für diese auch, und hatte noch nie ein Problem mit ihm.

Ein „Zeiger“, die ich gerade eine scharfe Erinnerung an in einem Stück Code gestern: wenn eine Zeichenfolge aus einem Block von binären Daten zu erstellen, verwenden Sie die std::string(startIter, endIter) Konstruktor Form, nicht die std::string(ptr, offset, length) Form - letzteres macht die Annahme, dass der Zeiger auf ein C-String und ignoriert alles nach den ersten Null-Zeichen (es Kopien „bis zu“ der angegebene length, nicht length Zeichen).

Sie sollten auf jeden Fall einige Container von char verwenden, aber der Container, den Sie verwenden möchten, hängt von Ihrer Anwendung.

Chars haben mehrere Eigenschaften, die sie nützlich für das Halten von Binärdaten zu machen: der Standard nicht zulässt, jede „padding“ für einen char-Datentyp, was wichtig ist, da es bedeutet, dass Sie nicht Müll in Ihrem binären Layout bekommen. Jedes Zeichen wird auch genau ein Byte sein garantiert, es ist der einzige gute alte Datentyp (POD) mit Schränkungsweite machen (alle andere sind angegeben in Bezug auf den oberen und / oder unteren Grenzen).

Die Diskussion über geeignete stl Behälter, mit denen die Zeichen zu speichern, wird gut von Doug oben behandelt. Welche Sie brauchen ganz auf Ihren Anwendungsfall abhängt. Wenn Sie nur einen Block von Datenhalten durch Sie durchlaufen, ohne spezielle Lookup, fügt / entfernen oder Spleiß Bedürfnisse, würde ich es vorziehen, Vektor, die Ihre Absichten deutlicher macht als std :: string, die viele Bibliotheken und Funktionen übernehmen werden hält einen nullterminierten c-String.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top