NULL



  • +fricky schrieb:

    C++ aber auch nicht, hat's alles von C übernommen, bis auf die kleine ausnahme mit dem void*
    🙂

    Haha, Du kennst C++ doch gar nicht richtig!



  • supertux schrieb:

    Oder kannst du eine Java Referenz auf jede beliebige Addresse des Addressraums zeigen lassen?

    Java Referenzen folgen der Semantik und Syntax der Pascal-Zeiger! Man kann lediglich keine Zeigerarithmetik wie in C machen, was per se kein Nachteil ist. Typsicherheit gilt für Zeiger (Java Referenzen) ebenfalls, aber das trifft auf andere Sprachen mit Zeiger auch zu.



  • +fricky schrieb:

    nö, in Java benutzt man dafür interfaces.

    Interfaces sind Mehrfachvererbung für Arme. Wenn man ein SmartPointer verwendet hat man keine Abhängigkeit im Sinne "erbt von" sondern "beinhaltet". Java muß man da auch Zeiger (Referenzen) verwenden. Bei Fowler & Co. finden sich Hinweise zum passenden Entwurf von Klassen.



  • +fricky schrieb:

    achso, noch mal 'ne frage zu c++ operatorüberladung: angenommen ich mache mir mit C++ 'ne klasse, die sinnvoll überladene shift-operatoren haben könnte (z.b. eine art schieberegister-simulation). kann ich den << zusätzlich noch als 'stream-output' operator überladen. ich meine ungefähr so:

    Ja, das geht problemlos, da die Typen der Argumente unterschiedlich sind.

    Den operator<< definiert man üblicherweise als reine Funktion, man kann ihn auch als Methode definieren, aber das hat andere Vor-/Nachteile.



  • Badestrand schrieb:

    Ich hab bis jetzt noch nie Operator-Überladung gesehen, die sich nicht intuitiv verhält ("do as the ints do").

    ich schon, z.b. eine klasse für komplexe zahlen, die den ^-operator (xor) zum potenzieren benutzt. und dieses stream-i/o zeugs << und >> ist uns allen ja bekannt.

    ~john schrieb:

    +fricky schrieb:

    C++ aber auch nicht, hat's alles von C übernommen, bis auf die kleine ausnahme mit dem void*
    🙂

    Haha, Du kennst C++ doch gar nicht richtig!

    es ging um's typsystem. c++ hat so gut wie nichts, was die typisierung sicherer macht, als von die von C. beide sprachen sind schwach typisiert.

    ~john schrieb:

    +fricky schrieb:

    nö, in Java benutzt man dafür interfaces.

    Interfaces sind Mehrfachvererbung für Arme.

    nenn es wie du willst. interfaces sind praktisch, wenn man verschiedene implementierungen für ähnliche dinge hat. du kannst damit festlegen, was ein objekt können soll, ohne konkret angeben zu müssen, um welches klasse von objekten es sich handelt.

    ~john schrieb:

    Wenn man ein SmartPointer verwendet hat man keine Abhängigkeit im Sinne "erbt von" sondern "beinhaltet". Java muß man da auch Zeiger (Referenzen) verwenden.

    wer redet hier von vererbung (ausser dir)? sicherlich verwendet java auch zeiger bzw. referenzen (sind ja sowieso das selbe), aber die brauchen nicht 'smart', sondern können ruhig ganz dumm sein, ohne das irgendwas schlimmes passiert.
    🙂



  • +fricky schrieb:

    Badestrand schrieb:

    Ich hab bis jetzt noch nie Operator-Überladung gesehen, die sich nicht intuitiv verhält ("do as the ints do").

    ich schon, z.b. eine klasse für komplexe zahlen, die den ^-operator (xor) zum potenzieren benutzt. und dieses stream-i/o zeugs << und >> ist uns allen ja bekannt.

    Die Stream-Operatoren zur Ausgabe sind in C++ doch intuitiv. '^' für pow ist natürlich ein Fehltritt.



  • Badestrand schrieb:

    +fricky schrieb:

    Badestrand schrieb:

    Ich hab bis jetzt noch nie Operator-Überladung gesehen, die sich nicht intuitiv verhält ("do as the ints do").

    ich schon, z.b. eine klasse für komplexe zahlen, die den ^-operator (xor) zum potenzieren benutzt. und dieses stream-i/o zeugs << und >> ist uns allen ja bekannt.

    Die Stream-Operatoren zur Ausgabe sind in C++ doch intuitiv. '^' für pow ist natürlich ein Fehltritt.

    '^' für pow wäre auch intuitiv. wenn die meisten es machen würden, wäre es was ganz normales. blöd dabei ist aber, dass die rangfolge von operatoren beim überladen nicht geändert werden kann. das hat der erfinder von C++ einfach vergessen.
    🙂



  • +fricky schrieb:

    Badestrand schrieb:

    Ich hab bis jetzt noch nie Operator-Überladung gesehen, die sich nicht intuitiv verhält ("do as the ints do").

    ich schon, z.b. eine klasse für komplexe zahlen, die den ^-operator (xor) zum potenzieren benutzt. und dieses stream-i/o zeugs << und >> ist uns allen ja bekannt.

    Link, falls es bei der in der Firma passiert ist, poste es bitte auf thedailywtf.com



  • +fricky schrieb:

    blöd dabei ist aber, dass die rangfolge von operatoren beim überladen nicht geändert werden kann. das hat der erfinder von C++ einfach vergessen.

    Du wetterst gegen Operatorüberladung weil es den Code ja achso unleserlich macht und willst aber ganz elementare Eigenschaften dieser gleich auch noch ändern können? Ich weiss ja dass du nur trollst, aber etwas weniger offensichtlich bitte 😉



  • Tim schrieb:

    Du wetterst gegen Operatorüberladung weil es den Code ja achso unleserlich macht und willst aber ganz elementare Eigenschaften dieser gleich auch noch ändern können?

    naja, es wäre doch 'ne verbesserung. dann könnte man dafür sorgen, dass ein überladener '^'-operator vor +,-,*,/, usw. kommt und ihn damit als 'pow' nutzen. die shifts werden doch auch schon anderweitig verwendet, ohne dass sich jemand dran stört.
    🙂



  • +fricky schrieb:

    Tim schrieb:

    Du wetterst gegen Operatorüberladung weil es den Code ja achso unleserlich macht und willst aber ganz elementare Eigenschaften dieser gleich auch noch ändern können?

    naja, es wäre doch 'ne verbesserung.

    Nein.

    Denn operatoren sind funktionen. EIne funktion multiply() hat sich immer gleich zu verhalten. Sie umzudefinieren ist genau das was an operator overloading kritisiert wird.

    Nur ist das halt alles sehr kurzsichtig. denn wenn + "add" heisst und * "multiply" dann sind das ganz normale funktionen mit einem ganz bestimmten verhalten. gerade wenn man überladung nicht hat: was macht folgender code:

    c=a.add(b);

    ändert sich a oder ändert es sich nicht?

    operator überladung verhindert zweideutigkeiten. deshalb ist sie gut.
    und statt ^ fürs potenzieren hätte der autor auch dingsDasHoch() nehmen können. wäre genauso ein schlechtes interface gewesen. ^ ist dagegen wunderschön eindeutig. und es fürs potenzieren zu verwenden zeugt nur von dummheit und sonst nix.



  • Badestrand schrieb:

    Die Stream-Operatoren zur Ausgabe sind in C++ doch intuitiv. '^' für pow ist natürlich ein Fehltritt.

    als ich das erste Mal je C++ Code sah (hello world), war meine erste Frage: "hä? link shift mit einem String?", ich hab's einfach nicht verstanden, was das sein soll, hab's einfach so akzeptiert. Erst später ist mir klar geworden, was das war (als ich zum Oprator-Überladung Kapitel gekommen bin). So intuitiv finde (und fand ich damals) es gar nicht.



  • supertux schrieb:

    Badestrand schrieb:

    Die Stream-Operatoren zur Ausgabe sind in C++ doch intuitiv. '^' für pow ist natürlich ein Fehltritt.

    als ich das erste Mal je C++ Code sah (hello world), war meine erste Frage: "hä? link shift mit einem String?", ich hab's einfach nicht verstanden, was das sein soll, hab's einfach so akzeptiert. Erst später ist mir klar geworden, was das war (als ich zum Oprator-Überladung Kapitel gekommen bin). So intuitiv finde (und fand ich damals) es gar nicht.

    Du warst aber nur verwirrt, weil du den Shift-Operator aus einer anderen Sprache (wohl C) kannstest. Aber mit dieser Voraussetzung sollte man an eine neue Sprache nicht rangehen. Weil sonst kann man nie ne neue Sprache designen, weil immer irgendjemand meint, er kennt das aber anders.

    Für mich pers. war das erste C++-Helloworld! sehr einleuchtend. Weil ich den Shift-Operator aus C nicht kannt, weil ich ebend kein C kannte (kannte nur Basic und Assembler). FÜr mich war das damals sonnenklar das der String in so ein cout "rein geht".



  • Ist ja alles richtig, aber als du dann das erste mal was gesehen hast wie 1<<30, was hast du dann gedacht? Da geht eine 30 in die 1 rein?



  • Und beim Thema shift-operatoren fandest du es auch total einleuchtend? Immerhin geht hier ja die 8 nicht in die 1 rein: 1<<8



  • tfa schrieb:

    Ist ja alles richtig, aber als du dann das erste mal was gesehen hast wie 1<<30, was hast du dann gedacht? Da geht eine 30 in die 1 rein?

    Es war sonnenklar, weil in dem Buch drin stand, das man damit Zahlen shiften kann. Und? Vielleicht bin ich auch nur zu doof, um das nicht zu verstehen. 🙄 C++ ist halt nichts für Schlauberger. 😃

    Aber im Ernst: C++ hat eine kontextabhängige Syntax. Das solle man schon mittlerweile mitbekommen haben.



  • Shade Of Mine schrieb:

    operator überladung verhindert zweideutigkeiten. deshalb ist sie gut.

    schon klar, deshalb kann man auch >> und << wahlweise als shift oder als stream-i/o operator benutzen.

    supertux schrieb:

    als ich das erste Mal je C++ Code sah (hello world), war meine erste Frage: "hä? link shift mit einem String?"

    frag' einen C-programmierer, was a<<b macht und er wird dir sagen 'nichts, weil die zuweisung fehlt'. wenn du die selbe frage an C++ programmierer richtest, würdest du wahrscheinlich so viele verschiedene antworten bekommen, wie du leute fragst.

    Artchi schrieb:

    Du warst aber nur verwirrt, weil du den Shift-Operator aus einer anderen Sprache (wohl C) kannstest. Aber mit dieser Voraussetzung sollte man an eine neue Sprache nicht rangehen.

    und du warst etwas später verwirrt, als du bemerktest, dass es den selben shift-op auch in C++ gibt, ne?
    🙂



  • Badestrand schrieb:

    Freigegeben wird alles automatisch, beim Fehler fliegt 'ne Exception. Ich hab bis jetzt noch nie Operator-Überladung gesehen, die sich nicht intuitiv verhält ("do as the ints do").

    Seit wann hat C++ einen anstaendigen GC? Und ein schlechtes Sprachfaeture (C++ exceptions) mit einem anderen zu kombinieren (op. ueberladung) kommen auch nur C++ler auf die Idee. Bis jetzt gibt es immer noch keinen einiges Beispiel fuer sinnvolle op.uberladung.

    Nur ist das halt alles sehr kurzsichtig. denn wenn + "add" heisst und * "multiply" dann sind das ganz normale funktionen mit einem ganz bestimmten verhalten. gerade wenn man überladung nicht hat: was macht folgender code:

    c=a.add(b);

    ändert sich a oder ändert es sich nicht?

    c = a + b;
    ändert sich a oder ändert es sich nicht? - In jeder anderen Sprache wuerde ich sagen, nein, in C++: Wer weis. Um Klarheit zu verschaffen muss ich mir die Dokumentation (wie bei jeder anderen Sprache auch) anschauen. Klar, der op+ sollte man in C++ als

    const X operator+(X const& lhs, X const& rhs);
    

    definieren, aber ist es die Regel? Und wenn die def. Zufaellig mal den Regeln erfolgt, gibt es immer noch const_cast oder andere Tricks.

    Nicht nur das sich die Def. der Operatoren unterscheiden kann, man kann sogar die Def. der gleichen Operatoren+Zuweisung veraendern. Wer garantiert mir das +,-,* und / sind genauso wie +=, -=, *= und /= verhalten?

    Das viel gepriesene

    Matrix a, b, c;
    c = a + b; // anstelle von c.add(a, b);
    

    Was passiert wenn es schief geht? Eine Art "Fehler-Matrix" zurueck zugeben? Oder eine exception zu werfen? Eine add() Funktion koennte einfach boolean zurueck geben.

    Nichtmal die C++ FAQ bringt gute Beispiele fuer op.uberladung.
    http://www.parashift.com/c++-faq-lite/operator-overloading.html#faq-13.3

    * myString + yourString might concatenate two std::string objects
    * myDate++ might increment a Date object
    * a * b might multiply two Number objects
    * a *might access an element of an Array object
    * x = p might dereference a "smart pointer" that "points" to a disk record — it could seek to the location on disk where p "points" and return the appropriate record into x

    dir + "/" + file
    

    das funktioniert wenn [i]dir* ein std::string und wenn file ein char* ist, aber nicht mehr wenn dir ein char* ist und file ein std::string. Ich sag nur

    std::ifstream in((std::string(dir) + "/" + file).c_str())
    
    1. myDate++, was soll das? Plus ein Jahr, ein Monat, oder ein Tag? Wenn myDate++ um Tage erhoeht, wieso ist dann myDate nicht einfach ein Integer.
      usw.


  • DEvent schrieb:

    c = a + b;
    ändert sich a oder ändert es sich nicht? - In jeder anderen Sprache wuerde ich sagen, nein, in C++: Wer weis.

    Nein. In C++ ändert sich a genausowenig wie in jeder anderen sprache.

    nur weil es die möglichkeit gibt das getSize() alle Elemente löscht, erwartest du es nicht, oder?

    Wer garantiert mir das +,-,* und / sind genauso wie +=, -=, *= und /= verhalten?

    der selbe der die garantiert dass list.clear() die liste löscht und list.getIterator() die liste nicht löscht - der gesunde menschenverstand.

    warum willst du operatoren anders behandeln als funktionen?

    Was passiert wenn es schief geht? Eine Art "Fehler-Matrix" zurueck zugeben? Oder eine exception zu werfen? Eine add() Funktion koennte einfach boolean zurueck geben.

    selbes problem bei
    a.add(b);

    die richtige antwort ist bei matrizen: compile error.
    oder wenn nicht anders geht: runtime error.

    1. myDate++, was soll das? Plus ein Jahr, ein Monat, oder ein Tag? Wenn myDate++ um Tage erhoeht, wieso ist dann myDate nicht einfach ein Integer.
      usw.

    das selbe wie myDate.inc();

    operatoren sind funktionen - behandle sie bitte so. wenn ich myDate.inc() implementiere bin ich ein vollkoffer. wenn ich myDate++ implementiere auch. Ich sehe einfach keinen unterschied zwischen diesen beiden sachen.



  • Shade Of Mine schrieb:

    operatoren sind funktionen - behandle sie bitte so. wenn ich myDate.inc() implementiere bin ich ein vollkoffer. wenn ich myDate++ implementiere auch. Ich sehe einfach keinen unterschied zwischen diesen beiden sachen.

    Genauso ist es. Aber anderes zu Funktionen haben Benutzer eine vorgefasste Meinung ueber Operatoren. Deswegen erhoeht es die Lesbarkeit nicht wenn man Op. ueberlaed. Es ist genauso sinnfrei einen ^-Operator als pow(x, y) zu missbrauchen wie die << und >> Operatoren fuer Streams.


Anmelden zum Antworten