it-swarm-eu.dev

Casts im C-Stil oder Casts im C ++ - Stil

Also, was benutzt du?

int anInt = (int)aFloat;

oder

int anInt = static_cast<int>(aFloat);
// and its brethren

Und was noch wichtiger ist, warum?

21
bastibe

Verstehen Sie zunächst, dass diese Zeilen nicht äquivalent sind .

int* anInt = (int*)aFloat; // is equivalent to

int* anInt = reinterpret_cast<int*>(aFloat); 

Was hier passiert, ist, dass der Programmierer den Compiler auffordert, alles zu tun, um die Besetzung zu machen.

Der Unterschied ist wichtig, da bei Verwendung von static_cast nur nach einem Basistyp gefragt wird, in den "sicher" konvertiert werden kann, wobei reinterpret_cast in alles konvertiert wird, möglicherweise nur durch Zuordnen des gewünschten Speicherlayouts zum Speicher des angegebenen Objekts.

Da der "Filter" nicht derselbe ist, ist die Verwendung einer bestimmten Umwandlung klarer und sicherer als die Verwendung der C-Umwandlung, wenn Sie sich auf den Compiler (oder die Laufzeitimpl. Wenn Sie dynamic_cast verwenden) verlassen, um zu erfahren, wo Sie etwas falsch gemacht haben durch Vermeiden von C cast und reinterepret_cast.

Jetzt, da dies klarer ist, gibt es noch etwas anderes: static_cast, reinterpret_cast, const_cast und dynamic_cast sind einfacher zu suchen .

Und der letzte Punkt: sie sind hässlich . Das ist erwünscht. Potenziell fehlerhafter Code, Code-Gerüche und offensichtliche "Tricks", die Fehler erzeugen können, sind leichter zu verfolgen, wenn sie mit hässlichem Aussehen verbunden sind. Schlechter Code sollte hässlich sein .

Das ist "beabsichtigt". Und das ermöglicht dem Entwickler zu wissen, wo er die Dinge besser hätte machen können (indem er Casts vollständig vermeidet, wenn sie nicht wirklich benötigt werden) und wo es in Ordnung ist, aber es ist im Code "dokumentiert", indem es als hässlich "markiert" wird.

Ein zweiter Grund für die Einführung der Besetzung im neuen Stil war, dass Besetzungen im C-Stil in einem Programm sehr schwer zu erkennen sind. Beispielsweise können Sie mit einem normalen Editor oder einem Textverarbeitungsprogramm nicht bequem nach Besetzungen suchen. Diese Unsichtbarkeit von Abgüssen im C-Stil ist besonders unglücklich, weil sie so potenziell schädlich sind. Eine hässliche Operation sollte eine hässliche syntaktische Form haben. Diese Beobachtung war Teil des Grundes für die Wahl der Syntax für die Casts neuen Stils. Ein weiterer Grund war, dass die Casts im neuen Stil mit der Template-Notation übereinstimmten, sodass Programmierer ihre eigenen Casts schreiben können, insbesondere zur Laufzeit überprüfte Casts.

Vielleicht, weil static_cast so hässlich und relativ schwer zu tippen ist, denken Sie eher zweimal nach, bevor Sie einen verwenden? Das wäre gut, denn Casts sind in modernem C++ meistens vermeidbar.

Quelle: Bjarne Stroustrup (C++ - Ersteller)

47
Klaim

C++ - Casts sind restriktiver (drücken Sie also Ihre Absicht besser aus und erleichtern Sie die Codeüberprüfung usw.). Sie sind auch viel einfacher zu suchen, wenn Sie es jemals brauchen.

37
Bruce Stephens

Option C: eine Besetzung im "C++ - Stil", da sie von einer Konstruktion nicht zu unterscheiden ist:

int anInt = int(aFloat);

oder auch:

int anInt(aFloat);

Abgesehen von diesen trivialen Fällen mit Grundelementen, die gut verstanden werden, bevorzuge ich die Verwendung von x_cast <> s gegenüber C-artigen Casts. Dafür gibt es drei Gründe:

  • Sie definieren die Operation, die der Programmierer ausführen wollte, enger.

  • Sie können Aktionen ausführen, die C-ähnliche Casts nicht können (insbesondere im Fall von dynamic_cast <>, das sich über Zweige einer Mehrfachvererbungskette hinweg übergreifen kann).

  • Sie sind hässlich. Sie erklären lautstark, dass der Programmierer gegen das Typsystem arbeitet. In diesem Fall ist es eine gute Sache.

13
Kaz Dragon

Ich habe einige Regeln für Casts im C/C++ - Stil:

  1. Das Deaktivieren einer Konstante muss immer einen const_cast Verwenden. Aus offensichtlichen Gründen. Leider wurde meine Regel über das Deaktivieren einer Konstante, die dazu führt, dass die Tastatur nach oben greift und den Finger des Programmierers bricht, nicht genehmigt.
  2. Alle Shenanigans im Bit-Manipulations-Stil, mit denen Programmierer auf dem Weg zum Metall sind, sollten reinterpret_cast Verwenden. Es ist wirklich die Art von Besetzung, die C nicht hat: Stellen Sie sich vor, die Bits dieser Ganzzahl seien tatsächlich die Bits eines Floats. Dies vermeidet Unannehmlichkeiten wie (int)(*(int*)(&floatVar)).
  3. Wenn Sie die Wörter "dynamic_cast" Eingeben, stoppen Sie und bewerten Sie Ihre polymorphe Klassenhierarchie und Ihr Design neu. Bewerten Sie das Design Ihrer Klassenhierarchie weiter, bis Sie diese Wörter löschen können.
  4. Kümmere dich nicht um static_cast.

Der Grund für # 4 ist einfach, dass es keine Rolle spielt. Die Umstände, die nicht in die anderen Regeln passen, sind entweder offensichtlich oder sehr niedrig. Eine gut verstandene Konvertierung einfacher Typen wie int-to-float sollte keine spezielle Syntax erfordern. Und wenn Sie in den tiefen, hässlichen Eingeweiden von etwas sind, dann sind Sie in den tiefen, hässlichen Eingeweiden von etwas. Es ist nicht nötig, auf die Tatsache aufmerksam zu machen, dass "hier Drachen sind", da die Zähne, Krallen und das Feuer es schon so ziemlich verraten haben.

7
Nicol Bolas

Wenn Sie Code in C schreiben, verwenden Sie eine C-Besetzung. Wenn Sie in C++ schreiben, verwenden Sie eine C++ - Besetzung.

Während die meisten Castings die ordnungsgemäße Typensicherheit beeinträchtigen, sind die C++ - Restriktionen restriktiver, und daher sind Sie etwas weniger typsicher als bei einem C-Cast.

Ich kann es tolerieren, dass jemand (T *) NULL verwendet, um eine Überlastung zu erzwingen ...

7
CashCow

Wie in den obigen Beiträgen erwähnt, ist die (statische) C++ - Besetzung in der Praxis etwas sicherer.

Es könnte klug sein, weitere Informationen über die verschiedenen Arten des Castings und ihre Vor- und Nachteile nachzuschlagen.

Nur um mehr Hintergrundwissen darüber zu haben, warum. .

http://en.wikipedia.org/wiki/Static_cast

http://en.wikipedia.org/wiki/Dynamic_cast

http://en.wikipedia.org/wiki/Reinterpret_cast

4
the JinX

Es kommt wirklich darauf an, mit welcher Sprache ich arbeite, da Sie wissen, was sie sagen: In Rom sprechen Sie Roman. Wenn ich also in C programmiere, versuche ich, die C-Funktionen maximal zu nutzen, aber wenn ich in C++ programmiere, verwende ich C++ - Funktionen maximal, auch wenn einige Leute diesen Ansatz nicht mögen, weil Sie sagen, es macht den Code "weniger portabel", ich sage, es ist mir egal, ich bin in C++ und programmiere in C++, und ich brauche einen vollständig C++ - kompatiblen Compiler, um Code zu kompilieren, sonst würde ich mit etwas anderem arbeiten an erster Stelle.

3
Coyote21

static_cast usw. wurden aufgrund von Problemen mit den C-Casts bei der Verwendung in Vorlagen erfunden. Wenn Sie eine Vorlage schreiben oder wenn Ihr Code später in eine Vorlage konvertiert wird, ist es eine gute Idee, Casts im C++ - Stil zu verwenden. Der Grund dafür ist, dass die Casts im C++ - Stil die Absicht besser ausdrücken, sodass sie die erwarteten Ergebnisse liefern, wenn Casts im C-Stil das Falsche tun (bestimmte Typen als Vorlagenparameter angegeben).

Abgesehen davon sage ich, verwenden Sie Casts im C++ - Stil, wenn Sie ein bestimmtes Problem haben, das sie benötigt - dynamic_cast ist das häufigste, aber selbst das ist wahrscheinlich nicht alltäglich.

Alles andere und eine Besetzung im C-Stil sind möglicherweise etwas unübersichtlicher und verbessern die Lesbarkeit oder hängen nicht davon ab, wie vertraut der Leser heutzutage mit dieser Besetzung ist. Es ist aus meiner Sicht nicht wirklich wichtig, meistens eine persönliche Präferenzsache, aber wundern Sie sich nicht, wenn einige Leute den C-Stil nicht mögen.

Schlussbemerkung - Wenn Sie so viele Casts benötigen, dass dies eine große Sache ist, machen Sie wahrscheinlich etwas anderes falsch. In einigen Fällen gibt es Ausnahmen, aber die meisten High-Level-Codes sollten nicht viele (wenn überhaupt) Casts benötigen.

3
Steve314