Was für einen Sinn hat der <<-Operator?



  • Hallo Leute,

    möchte ich einen Text auf der Konsole ausgeben, kann man das mit der cout-Klasse umsetzen:

    cout << "Hallo!" << endl;
    

    Doch woher kommt der <<-Operator? Wieso verwendet man keine Parameterübergabe an eine Funktion? Wie kann man eine eigene Klasse programmieren, die den <<-Operator verwendet?

    Dummkopf 😕



  • Das ist ein Stream. Google mal danach...


  • Administrator

    Dazu haben wir einen Artikel im Magazin:
    Überladung von Operatoren (Teil 1)

    Teil 2 ist gerade erst erschienen, ist noch nicht mal im Inhaltsverzeichnis aufgeführt. Daher erstmal nur hier zu finden:
    http://www.c-plusplus.net/forum/viewtopic-var-t-is-240706.html

    Grüssli


  • Mod

    Die anderen beiden Fragen wurden ja schon beantwortet:

    Dummkopf schrieb:

    Wieso verwendet man keine Parameterübergabe an eine Funktion?

    Du denkst wahrscheinlich an sowas wie printf in C. Das Problem bei der Übergabe an eine Funktion ist zweierlei:

    1. Die Übergabe: Die auszugebenen Daten müssen irgendwie an die Funktion übergeben werden. Eigentlich müsste man für jeden Datentyp eine neue Funktion schreiben, damit man ihr den entsprechenden Typ übergeben kann. Das ist aber extrem unpraktisch. Bei der printf-Funktion behilft man sich dadurch, dass die Funktion erstmal alles annimmt und man ihr im Formatstring angibt, was man da übergeben hat. Das ist aber kein sicheres Konzept, da man nicht sicher wissen kann, ob der Programmierer nicht gelogen oder sich vertan hat und die übergebenen Daten auch wirklich von dem Typ sind den er angegeben hat.
    2. Die Ausgabe: C kennt eine handvoll primitiver Datentypen und printf ist in der Lage diese auszugeben. Was ist aber in C++, wo man eigene Datentypen hat? Im Prinzip müsste man für jede Klasse ein eigenes printf schreiben. Das entspricht aber nicht der objektorientierten Denkweise: Die Daten sollten selber wissen, wie sie ausgegeben werden.

    Und beide Probleme löst der << Operator: Indem man seinen eigenen Klassen einen << Operator verpasst, teilt man mit, wie die Daten ausgegeben werden sollen. Und dies stellt auch sicher, dass nur ausgebbare Daten ausgegeben werden - und das auf korrekte Weise.


  • Administrator

    SeppJ schrieb:

    Eigentlich müsste man für jeden Datentyp eine neue Funktion schreiben, damit man ihr den entsprechenden Typ übergeben kann. Das ist aber extrem unpraktisch.

    Wird in C++ aber genau so gehandhabt. Daher ein wenig ein seltsames Argument 😉

    SeppJ schrieb:

    Die Ausgabe: C kennt eine handvoll primitiver Datentypen und printf ist in der Lage diese auszugeben. Was ist aber in C++, wo man eigene Datentypen hat? Im Prinzip müsste man für jede Klasse ein eigenes printf schreiben.

    Das deutlich grössere Problem an printf ist, dass es nur primitive Typen behandeln kann, denn über die Ellipse kann man nur primitive Typen übergeben. In C++ schreibt man schliesslich auch für jede Ausgabe der eigenen Klasse eine eigene Funktion.

    SeppJ schrieb:

    Das entspricht aber nicht der objektorientierten Denkweise: Die Daten sollten selber wissen, wie sie ausgegeben werden.

    Das entspricht auch nicht der objektorientierten Denkweise. Die Daten sollte überhaupt nicht wissen, wie sie ausgegeben werden. Das ist normalerweise die Aufgabe der View. Siehe MVC:
    http://de.wikipedia.org/wiki/MVC

    Die C++ Stream sind nicht optimal. Das wurde schon mehrmals erwähnt. Aber sie sind ein möglicher Lösungsansatz.

    SeppJ schrieb:

    Und beide Probleme löst der << Operator:

    Wie oben erläutert stimmt dies nicht 😉

    Grüssli



  • Hallo,

    @Dravere: Bist du dir sicher, dass das MVC-Pattern in C++ bzw. bei der cout-Klasse umgesetzt ist? Möchte man das MVC-Pattern verwenden, muss man erst eine Instaz von der Controller-Klasse erstellen und festlegen, womit die Klasse interagieren soll. Das cout ist in meinen Augen nichts weiter als eine Klasse.

    Aber warum wird nicht eine generische Klasse verwendet, womit man alle Typen anzeigen lassen kann? Wie programmiert man den eine Klasse, mit der man auch den <<- bzw. >>-Operator verwenden kann?

    Dummkopf



  • Dazu müsstest du dir mal die Grundlagen anschauen...
    Und Dravere hat dir auch schon einen Link zu dem Magazin gegeben wo das beschrieben steht.
    Ansonsten gebe ich dir soweit Recht das MVC ein Pattern ist aber das nicht wirklich etwas direkt mit Objektorientierung zu tun hat... Es ist, wie die meisten Pattern, unabhängig von der Sprache...
    Eine generische Klasse könnte man auch über Templates realisieren die sowas ausgibt, da müsste man aber jedes mal den Typ mit angeben, was doof ist wenn man mehrere Typen ausgeben will...
    Ich bin mit cout und cin sehr zufrieden da es Typsicher ist und auch mit komplexen Datentypen und Klassen funktioniert.


  • Administrator

    Dummkopf schrieb:

    @Dravere: Bist du dir sicher, dass das MVC-Pattern in C++ bzw. bei der cout-Klasse umgesetzt ist?

    Zuerst muss du mir zeigen, wo ich sowas gesagt habe. Ich habe nur SeppJ korrigiert, was seine Ansicht von Objektorientierung angeht. Das hatte nichts mit C++ oder std::cout zu tun.

    Dummkopf schrieb:

    Das cout ist in meinen Augen nichts weiter als eine Klasse.

    Nein, std::cout ist ein Objekt von folgendem oder davon abgeleitetem Typ:
    std::basic_ostream<char>

    Dummkopf schrieb:

    Aber warum wird nicht eine generische Klasse verwendet, womit man alle Typen anzeigen lassen kann?

    Und wie willst du das umsetzen? Woher soll diese Klasse wissen, wie man zum Beispiel ein Rechteck ausgibt?

    Dummkopf schrieb:

    Wie programmiert man den eine Klasse, mit der man auch den <<- bzw. >>-Operator verwenden kann?

    Lies ein C++ Buch, lies ein C++ Tutorial oder lies den Artikel, welchen ich verlinkt habe.

    Grüssli



  • Nein, cout ist eine Klasse. Ein Objekt ist es, wenn eine Instanz der Klasse erstellt worden ist. Man könnte statt einer generischen Klasse ein Objekt-Typ doch als Parameter einer Funktion verwenden.

    Aber was solls. Danke für eure Hilfe!


  • Administrator

    Dummkopf schrieb:

    Nein, cout ist eine Klasse.

    Nein, ist es nicht.

    Dummkopf schrieb:

    Ein Objekt ist es, wenn eine Instanz der Klasse erstellt worden ist.

    Und std::cout ist eine Instanz der Klasse std::basic_ostream<char> oder einer davon abgeleiteten Klasse. Folglich ist std::cout ein Objekt.

    Dummkopf schrieb:

    Man könnte statt einer generischen Klasse ein Objekt-Typ doch als Parameter einer Funktion verwenden.

    Und weiter? Dann müsstest du ja immer noch irgendwie definieren, wie dieser Objekttyp behandelt werden soll.

    Grüssli



  • Nicht böse sein, aber da scheint es noch ganz arg am Grundlagenverständnis zu hapern.


Anmelden zum Antworten