Funktionsparameter const * const - Sinn des zweiten const?

Programmiersprachen, APIs, Bibliotheken, Open Source Engines, Debugging, Quellcode Fehler und alles was mit praktischer Programmierung zu tun hat.
Antworten
kaiserludi
Establishment
Beiträge: 467
Registriert: 18.04.2002, 15:31

Funktionsparameter const * const - Sinn des zweiten const?

Beitrag von kaiserludi »

Moin.

Wenn man von const-Correctness spricht, sieht man oft Code wie diesen als propagierte Ideallösung: void foo(const int* const foobar);

Wo ist der Vorteil gegenüber void foo(const int* foobar); ?

Im ersten Fall ist nicht nur die Variable, auf die der Pointer zeigt, konstant, sondern zusätzlich auch noch der Pointer selbst, das ist mir klar.

Aber was bringt es, den Pointer const zu machen? Er wird doch eh per value kopiert?

Man schreibt ja schließlich auch nicht void foo(const int foobar);, sondern schlicht void foo(int foobar);, weil der Parameter eh kopiert wird und man das Original so eh nicht verändern kann, egal ob const oder nicht. Das selbe trifft doch auch auf das const von int* const zu?
"Mir ist auch klar, dass der Tag, an dem ZFX und Developia zusammengehen werden der selbe Tag sein wird, an dem DirectGL rauskommt."
DirectGL, endlich ist es da
:)

"According to the C++ standard, it's "undefined". That's a technical term that means, in theory, anything can happen: the program can crash, or keep running but generate garbage results, or send Bjarne Stroustrup an e-mail saying how ugly you are and how funny your mother dresses you." :shock:[/size]
Benutzeravatar
donelik
Beiträge: 56
Registriert: 28.11.2006, 17:49
Benutzertext: Will releasen!
Kontaktdaten:

Re: Funktionsparameter const * const - Sinn des zweiten cons

Beitrag von donelik »

Dass du ihn innerhalb der Funktion nicht versehentlich ändern kannst. Halt derselbe Grund, aus dem du lokale const deklarierst. Ich persönlich "markiere" ja die Gültigkeit eine Variable gern mit dem Präfixen g_, m_ oder l_ ... und "l_"s werden bei mir nie überschrieben.
Ach hör' auf ...
kaiserludi
Establishment
Beiträge: 467
Registriert: 18.04.2002, 15:31

Re: Funktionsparameter const * const - Sinn des zweiten cons

Beitrag von kaiserludi »

Sprich, für den Aufrufer der Funktion ist es genauso irrelevant wie ob ich rein lokale Variablen const mache oder nicht?
"Mir ist auch klar, dass der Tag, an dem ZFX und Developia zusammengehen werden der selbe Tag sein wird, an dem DirectGL rauskommt."
DirectGL, endlich ist es da
:)

"According to the C++ standard, it's "undefined". That's a technical term that means, in theory, anything can happen: the program can crash, or keep running but generate garbage results, or send Bjarne Stroustrup an e-mail saying how ugly you are and how funny your mother dresses you." :shock:[/size]
Benutzeravatar
Aramis
Moderator
Beiträge: 1458
Registriert: 25.02.2009, 19:50
Echter Name: Alexander Gessler
Wohnort: 2016
Kontaktdaten:

Re: Funktionsparameter const * const - Sinn des zweiten cons

Beitrag von Aramis »

Der einzige nennenswerte Zweck waere, dass der Compiler evtl. in der Lage ist, die Funktion besser zu optimieren da es ja klar ist, dass sich die Parameter nicht aendern koennen. Letztlich ist das Argument aber hinfaellig, denn das findet der Compiler auch locker ohne das const heraus.

Ausserdem ist es eigentlich ein Implementierungsdetail ob eine Funktion by-value empfangene Parameter intern modifiziert oder nicht. Insofern hat es eigentlich im Funktionsprototyp - der ja die oeffentliche Schnittstelle spezifiziert - nichts verloren.
kaiserludi
Establishment
Beiträge: 467
Registriert: 18.04.2002, 15:31

Re: Funktionsparameter const * const - Sinn des zweiten cons

Beitrag von kaiserludi »

Aramis hat geschrieben:Der einzige nennenswerte Zweck waere, dass der Compiler evtl. in der Lage ist, die Funktion besser zu optimieren da es ja klar ist, dass sich die Parameter nicht aendern koennen. Letztlich ist das Argument aber hinfaellig, denn das findet der Compiler auch locker ohne das const heraus.
Der Compiler kann sich da doch eh nicht auf das const alleine verlassen, sondern muss so oder so in den Funktionsrumpf schauen, da ich das const ja wegcasten könnte.
Aramis hat geschrieben: Ausserdem ist es eigentlich ein Implementierungsdetail ob eine Funktion by-value empfangene Parameter intern modifiziert oder nicht. Insofern hat es eigentlich im Funktionsprototyp - der ja die oeffentliche Schnittstelle spezifiziert - nichts verloren.
Genau das war auch mein Gedanke.
"Mir ist auch klar, dass der Tag, an dem ZFX und Developia zusammengehen werden der selbe Tag sein wird, an dem DirectGL rauskommt."
DirectGL, endlich ist es da
:)

"According to the C++ standard, it's "undefined". That's a technical term that means, in theory, anything can happen: the program can crash, or keep running but generate garbage results, or send Bjarne Stroustrup an e-mail saying how ugly you are and how funny your mother dresses you." :shock:[/size]
Benutzeravatar
Krishty
Establishment
Beiträge: 8244
Registriert: 26.02.2009, 11:18
Benutzertext: state is the enemy
Kontaktdaten:

Re: Funktionsparameter const * const - Sinn des zweiten cons

Beitrag von Krishty »

kaiserludi hat geschrieben:Der Compiler kann sich da doch eh nicht auf das const alleine verlassen, sondern muss so oder so in den Funktionsrumpf schauen, da ich das const ja wegcasten könnte.
Muss er nicht. In Objekte zu schreiben, die das Resultat von const_cast sind, ist Undefined Behavior. Der Compiler/Optimizer kann jede Wirkung, die durch const_cast eintritt, einfach ignorieren. (Es sei denn, das Ziel ist mutable deklariert – aber dann kann er sowieso nicht optimieren.)

Was Aramis mit dem Implementierungsdetail angesprochen hat, hat übrigens eine nützliche Wirkung: Du kannst by-Value-Parameter in der Funktionsdeklaration deklarieren, wie es dir lustig ist, und in der Funktionsdefinition nachträglich mit const dekorieren, ohne, dass es jemanden stören würde.
seziert Ace Combat, Driver, und S.T.A.L.K.E.R.   —   rendert Sterne
kaiserludi
Establishment
Beiträge: 467
Registriert: 18.04.2002, 15:31

Re: Funktionsparameter const * const - Sinn des zweiten cons

Beitrag von kaiserludi »

Krishty hat geschrieben:
kaiserludi hat geschrieben:Der Compiler kann sich da doch eh nicht auf das const alleine verlassen, sondern muss so oder so in den Funktionsrumpf schauen, da ich das const ja wegcasten könnte.
Muss er nicht. In Objekte zu schreiben, die das Resultat von const_cast sind, ist Undefined Behavior. Der Compiler/Optimizer kann jede Wirkung, die durch const_cast eintritt, einfach ignorieren. (Es sei denn, das Ziel ist mutable deklariert – aber dann kann er sowieso nicht optimieren.)
WTF?
Das heißt, wenn ich eine const-Variable bekomme, caste das const weg und schreibe einen neuen Wert rein, dann kann das kompilieren und mir zur Laufzeit um die Ohren fliegen, weil der Compiler es so optimiert hat, dass ein Schreibzugriff es abschmieren lässt?
Krishty hat geschrieben: Was Aramis mit dem Implementierungsdetail angesprochen hat, hat übrigens eine nützliche Wirkung: Du kannst by-Value-Parameter in der Funktionsdeklaration deklarieren, wie es dir lustig ist, und in der Funktionsdefinition nachträglich mit const dekorieren, ohne, dass es jemanden stören würde.
Doch, das stört z.B. docomatic, welches nicht damit klar kommt, wenn sich Deklaration und Definition unterscheiden, selbst wenn es nur whitespaces sind. z.B. Deklaration void a(int* b); vs. void Definition a(int *b){} mit Doku in der Definition geschrieben findet es die Doku nicht mehr...
"Mir ist auch klar, dass der Tag, an dem ZFX und Developia zusammengehen werden der selbe Tag sein wird, an dem DirectGL rauskommt."
DirectGL, endlich ist es da
:)

"According to the C++ standard, it's "undefined". That's a technical term that means, in theory, anything can happen: the program can crash, or keep running but generate garbage results, or send Bjarne Stroustrup an e-mail saying how ugly you are and how funny your mother dresses you." :shock:[/size]
Benutzeravatar
Krishty
Establishment
Beiträge: 8244
Registriert: 26.02.2009, 11:18
Benutzertext: state is the enemy
Kontaktdaten:

Re: Funktionsparameter const * const - Sinn des zweiten cons

Beitrag von Krishty »

kaiserludi hat geschrieben:WTF?
Das heißt, wenn ich eine const-Variable bekomme, caste das const weg und schreibe einen neuen Wert rein, dann kann das kompilieren und mir zur Laufzeit um die Ohren fliegen, weil der Compiler es so optimiert hat, dass ein Schreibzugriff es abschmieren lässt?
Falls es sich um eine POD-Variable handelt, stünde es dem Compiler frei, sie im Datensegment unterzubringen. (Nicht nur bei POD – da die Sprache als solche kein Datensegment kennt, könnte das überall geschehen; bei landläufigen Compilern aber eben nur bei const POD.) Das wird üblicherweise zu read-only kompiliert und deshalb dein Programm beim Schreibzugriff beendet, ja. Bei der Mehrheit der Variablen würde das aber nur mit böser Absicht des Compiler-Herstellers geschehen ;) Wahrscheinlicher ist, dass die Schreiboperationen einfach wegoptimiert werden und garnicht stattfinden. Unter Visual C++ würde ich jetzt ins Blaue raten, dass sie tatsächlich nach const_cast suchen und Schreiboperationen durchführen, damit sich nicht so viele ahnungslose Leute beschweren, der Compiler würde nicht funktionieren (und damit man es bei Low-Level-Hacks einfacher hat) – wäre ja nicht das erste Mal.

Der Punkt ist: Du sagst irgendwo weit oben im Programm, die Funktion hätte keine Wirkung. Und ganz unten sagst du dann: Hat sie doch. Für die Programmkonsistenz ist das eine Lose-Lose-Situation und genau die Art von Doppelbindung, die in Science-Fiction-Filmen den Roboter zum Töten aller Menschen veranlasst. Darum darf es in standardkonformen C++-Programmen nicht vorkommen (aus dem ersten Grund – aus dem zweiten hypothetisch, falls ich den Standard formuliert hätte).
kaiserludi hat geschrieben:Doch, das stört z.B. docomatic, welches nicht damit klar kommt, wenn sich Deklaration und Definition unterscheiden, selbst wenn es nur whitespaces sind.
Ich hatte das „jemanden“ auf die Sprache, standardkonforme Compiler und wissende Programmierer bezogen ;) Aber falls das mit den Whitespaces stimmt, ist das eh ein lächerliches Scheißteil.

Achja: Ich hatte noch was von sowieso-nicht-optimierten mutable-Variablen geschrieben … das war Schmu. Da hatte ich tatsächlich mutable mit volatile durcheinandergeschmissen, aua :?
seziert Ace Combat, Driver, und S.T.A.L.K.E.R.   —   rendert Sterne
kaiserludi
Establishment
Beiträge: 467
Registriert: 18.04.2002, 15:31

Re: Funktionsparameter const * const - Sinn des zweiten cons

Beitrag von kaiserludi »

Krishty hat geschrieben: Der Punkt ist: Du sagst irgendwo weit oben im Programm, die Funktion hätte keine Wirkung. Und ganz unten sagst du dann: Hat sie doch. Für die Programmkonsistenz ist das eine Lose-Lose-Situation und genau die Art von Doppelbindung, die in Science-Fiction-Filmen den Roboter zum Töten aller Menschen veranlasst. Darum darf es in standardkonformen C++-Programmen nicht vorkommen (aus dem ersten Grund – aus dem zweiten hypothetisch, falls ich den Standard formuliert hätte).?
Untersagt der Standard das ausdrücklich? Ich bin bisher davon ausgegangen, dass es einfach nur grausig schlechter Stil ist.
"Mir ist auch klar, dass der Tag, an dem ZFX und Developia zusammengehen werden der selbe Tag sein wird, an dem DirectGL rauskommt."
DirectGL, endlich ist es da
:)

"According to the C++ standard, it's "undefined". That's a technical term that means, in theory, anything can happen: the program can crash, or keep running but generate garbage results, or send Bjarne Stroustrup an e-mail saying how ugly you are and how funny your mother dresses you." :shock:[/size]
Benutzeravatar
Krishty
Establishment
Beiträge: 8244
Registriert: 26.02.2009, 11:18
Benutzertext: state is the enemy
Kontaktdaten:

Re: Funktionsparameter const * const - Sinn des zweiten cons

Beitrag von Krishty »

C++0x Draft hat geschrieben:§5.2.11 Const cast
7 [Note: Depending on the type of the object, a write operation through the pointer, lvalue or pointer to data member resulting from a const_cast that casts away a const-qualifier72 may produce undefined behavior (7.1.6.1). —end note ]

§7.1.6.1 The cv-qualifiers
4 Except that any class member declared mutable (7.1.1) can be modified, any attempt to modify a const object during its lifetime (3.8) results in undefined behavior.
Ist es nicht mutable, du castest const weg und modifizierst es, ist es undefiniert.

const ist halt nicht bloß eine Empfehlung, wie z.B. das register-Schlüsselwort, sondern eine beinharte Regel. Sonst wäre es ja auch nutzlos.
seziert Ace Combat, Driver, und S.T.A.L.K.E.R.   —   rendert Sterne
Antworten