klasse nicht geklariert, obwohl sie es sein müsste?!



  • Dobi schrieb:

    ...Für meinen Geschmack ist das eher ne Frickellösung, weil kein Compiler "export" hinbekommen hat...

    Diese Aussage stimmt nicht ganz, mindestens der Comeau Compiler hat dies tatsächlich (mit sehr langer Entwicklungszeit) hinbekommen, nun fällt das mit dem neuen Standard aber eh wieder weg (Dürfte für den Comeau-Entwickler recht ärgerlich sein, anderseits ärgere ich mich wiederum über die extrem langen Zyklen beim Comeau...).



  • Dobi schrieb:

    Ok. Jetzt interessiert mich noch, wie du das mit den Inlinememberfunktionen in normalen Klassen machst. 🙂

    Was soll damit sein?



  • Ok, wenn du bei nichttemplatigen Klassen auch Foo.h, Foo_sichtbare_Definitionen.cpp und Foo_unsichtbare_Definitionen.cpp benutzt, erübrigt sich die Frage natürlich. 😉



  • also ich mach das immer folgendermaßen mit klassen die sowohl template-funktionen als auch nicht template funktionen hat:
    header foo.h

    #ifndef __foo_h__
    #define __foo_h__
    
    class foo
    {
      //normale- und template-funktion deklarationen
    };
    
    #ifndef __foo_template__
    #define __foo_template__
    
    #include "foo.cpp"
    
    #undef __foo_template__
    #endif
    
    #endif
    

    definition foo.cpp

    #ifndef __foo_cpp__
    #define __foo_cpp__
    
    #include "foo.h"
    
    #ifndef __foo_template__
    //nicht-template-funktion definitionen
    #endif
    
    //template-funktion definitionen
    
    #endif
    

    das funktioniert bis jetzt immer sehr gut. wenn es allerdings ein problem damit gibt, wäre ich natürlich interessiert es zu erfahren.



  • FreakyBKA schrieb:

    das funktioniert bis jetzt immer sehr gut. wenn es allerdings ein problem damit gibt, wäre ich natürlich interessiert es zu erfahren.

    Das funktioniert solange gut, bis du mit jemand anderem zusammenarbeitest. Der wird dich nämlich wegen der Spaghetti-includes in der Kaffeetasse ertränken...
    Wer soll sowas denn nachvollziehen?

    Und das alles nur, damit die Definitionen der Template-Funktionen nicht im Header stehn müssen?



  • also ich für meinen geschmack finde es gut wenn deklarationen und definitionen getrennt sind. wenn dann soll er mich bitte im tee ertränken, ich trink nämlich keinen kaffee 😉
    gibts irgendwelche anderweitigen probleme mit dieser umsetzung, die nichts mit dem geschmack bzgl. des programmierstils zu tun haben :p



  • FreakyBKA schrieb:

    also ich für meinen geschmack finde es gut wenn deklarationen und definitionen getrennt sind.

    Finde ich auch gut, aber trotzdem komme ich ohne das Gefrickel klar. Warum lagerst du die Funktionstemplate-Definitionen nicht in eine separate .inl-Datei aus, die du am Ende des Headers inkludierst?



  • Ja, gibt es 😉
    Sobald du nämlich eine Library entwickelst und nur die Header weitergeben willst...



  • also mit library-entwicklung hab ich mich noch nicht auseinandergesetzt, weiß auch nicht wie das geht, gibts dafür literatur oder gute online-quellen?
    dabei stell ich mir auch grad die frage warum man nur die header reinpacken sollte, müssen die definitionen nicht auch irgendwie mit rein?



  • Dobi schrieb:

    Ok, wenn du bei nichttemplatigen Klassen auch Foo.h, Foo_sichtbare_Definitionen.cpp und Foo_unsichtbare_Definitionen.cpp benutzt, erübrigt sich die Frage natürlich. 😉

    Och, jetzt komm aber, ist das dein Ernst? 🙂
    Wer so engstirnig ist, dem ist nicht mehr zu helfen. Einen primitiven Konstruktor schreib ich zB natürlich auch gleich anstatt einer Deklaration fertig hin.
    Du würdest also, wenn dadurch keine Redundanzen mit doppeltem Code entstehen würden, einfach alles in ein File reinschreiben? 😉

    Im Endeffekt ist das doch ganz einfach ein doch noch recht simpler(!) Versuch, separation zumindest "filetechnisch" auch ohne export hinzukriegen. Und separation ist doch immer noch eines der Grundprinzipien von C++ und zumindest meiner Meinung nach der Übersicht recht dienlich.

    pumuckl schrieb:

    Wer soll sowas denn nachvollziehen?

    Ja wirklich seehr anspruchsvoll 😉 Da programmiert man die kompliziertesten Konstrukte, wo x Funktionen und Objekte miteinander zusammenspielen müssen, aber sowas ist dann zuviel..?

    @FreakyBKA: Das läuft perfekt, solange du weisst, was du tust 🤡



  • ccpete schrieb:

    pumuckl schrieb:

    Wer soll sowas denn nachvollziehen?

    Ja wirklich seehr anspruchsvoll 😉 Da programmiert man die kompliziertesten Konstrukte, wo x Funktionen und Objekte miteinander zusammenspielen müssen, aber sowas ist dann zuviel..?

    Unnötige Komplexität ist zuviel, ja. Klar kann man sowas machen, und wenn der Kollege, der den Kram am Ende warten muss, genug Zeit rein steckt, wird er es sicher auch nachvollziehen können. Trotzdem gilt, dass Klarheit und Einfachheit gewinnt. Das gilt auch für die komplizierten Konstrukte mit den x Funktionen und Objekten. Die kann man meistens so entheddern (durch Indirektion und Kapselung), dass x relativ klein (einstellig) wird.



  • Nexus schrieb:

    Warum lagerst du die Funktionstemplate-Definitionen nicht in eine separate .inl-Datei aus, die du am Ende des Headers inkludierst?

    Auch schön.

    pumuckl schrieb:

    Unnötige Komplexität ist zuviel, ja. Klar kann man sowas machen, und wenn der Kollege, der den Kram am Ende warten muss, genug Zeit rein steckt, wird er es sicher auch nachvollziehen können. Trotzdem gilt, dass Klarheit und Einfachheit gewinnt. Das gilt auch für die komplizierten Konstrukte mit den x Funktionen und Objekten. Die kann man meistens so entheddern (durch Indirektion und Kapselung), dass x relativ klein (einstellig) wird.

    Komplexität ist schon ein Argument, auf der anderen Seite ist dies ja nicht wirklich aufwändig. Höchstens vielleicht ungewohnt und deshalb irritierend?
    Kapselung ist ja genau was hier geschieht 😉



  • ccpete schrieb:

    Dobi schrieb:

    Ok, wenn du bei nichttemplatigen Klassen auch Foo.h, Foo_sichtbare_Definitionen.cpp und Foo_unsichtbare_Definitionen.cpp benutzt, erübrigt sich die Frage natürlich. 😉

    Och, jetzt komm aber, ist das dein Ernst? 🙂
    Wer so engstirnig ist, dem ist nicht mehr zu helfen. Einen primitiven Konstruktor schreib ich zB natürlich auch gleich anstatt einer Deklaration fertig hin.
    Du würdest also, wenn dadurch keine Redundanzen mit doppeltem Code entstehen würden, einfach alles in ein File reinschreiben? 😉

    Ich hab nicht gesagt, dass ich es so engstirnig machen würde, mich hat nur interessiert, wie du das in dem Konzept umsetzt. 😉

    ccpete schrieb:

    Kapselung ist ja genau was hier geschieht 😉

    Kapselung hat für mich bisher immer eher bedeutet, irgendwas gegen Zugriff zu schützen, und nicht, dass man öffentliche Sachen auf mehrere Dateien aufteilt, was man aber natürlich trotzdem tun kann.



  • ccpete schrieb:

    Nexus schrieb:

    Warum lagerst du die Funktionstemplate-Definitionen nicht in eine separate .inl-Datei aus, die du am Ende des Headers inkludierst?

    Auch schön.

    Schön. Ohne auch.

    ccpete schrieb:

    Nexus schrieb:

    Warum lagerst du die Funktionstemplate-Definitionen nicht in eine separate .inl-Datei aus, die du am Ende des Headers inkludierst?

    Auch schön.

    Schön. Ohne auch. Denn diese template-include-guards sind einfach unnötig und das Ganze deshalb nicht schön. Um das mal gegenüberzustellen:

    Version von FreakyBKA

    //================= header foo.h
    #ifndef __foo_h__
    #define __foo_h__
    
    class foo
    {
      //normale- und template-funktion deklarationen
    };
    
    #ifndef __foo_template__
    #define __foo_template__
    
    #include "foo.cpp"
    
    #undef __foo_template__
    #endif
    
    #endif
    
    //================= definition foo.cpp
    #ifndef __foo_cpp__
    #define __foo_cpp__
    
    #include "foo.h"
    
    #ifndef __foo_template__
    //nicht-template-funktion definitionen
    #endif
    
    //template-funktion definitionen
    
    #endif
    

    Version Nexus:

    //================= header foo.h
    #ifndef __foo_h__
    #define __foo_h__
    
    class foo
    {
      //normale- und template-funktion deklarationen
    };
    
    #include "foo.inl"
    #endif
    
    //================== inl-Datei mit Template Definitionen:
    //template-funktion definitionen
    
    //================= definition foo.cpp
    #include "foo.h"
    
    //nicht-template-funktion definitionen
    

    Die zweite Version kommt (außer den normalen include-guards im Header) ohne die ganzen unkonventionellen und daher verwirrenden extra-guards aus. Dazu ist die Möglichkeit gegeben, wie Th69 schon schreibt, Bibliotheken zu erstellen, ohne die implementierung der nicht-template-funktionen in das interface zu packen, wo sie nichts verloren hat (weil das eben NICHT dem Prinzip der Kapselung entspricht). Natürlich wird sie, da nur der Header eingebunden wird, nie vom Compiler ausgewertet. Das ist aber noch ein zusätzlicher Grund, warum sie nicht mitgeliefert werden sollte. Dazu kommt, dass die Klienten von foo nicht nur den Header zur Verfügung haben müssen, sondern auch eine .cpp - und eine .cpp, die nicht übersetzt wird, ist nochmal extra komisch. Dann lieber die .inl, am besten mit einem entsprechenden Kommentar in der ersten Zeile, dass es sich um Template-Definitionen handelt.

    Es ist wie so vieles Geschmackssache. Allerdings gibts grade bei sowas ein bis zwei übliche, "glatte" Lösungen (.h ohne definitionen plus .inl, oder .h mit definitonen), und alle weniger üblichen und unnötig komplizierteren Lösungen stoßen bei der Mehrheit auf Unverständnis und Unwillen, wenn sie gezwungen werden, damit zu arbeiten.



  • Vielleicht sollte man nochmal drauf hinweisen dass Namen die mit zwei Underscores beginnen reserviert sind. Include Guards wie __foo_h__ sind also genaugenommen undefiniertes Verhalten und damit keine gute Idee.



  • Dobi schrieb:

    Ich hab nicht gesagt, dass ich es so engstirnig machen würde, mich hat nur interessiert, wie du das in dem Konzept umsetzt.

    Und ich wollte damit nicht ausdrücken, dass ich dir unterstelle, so engstirnig zu sein, sondern dass ich es nicht bin 😉

    pumuckl schrieb:

    Allerdings gibts grade bei sowas ein bis zwei übliche, "glatte" Lösungen (.h ohne definitionen plus .inl, oder .h mit definitonen), und alle weniger üblichen und unnötig komplizierteren Lösungen stoßen bei der Mehrheit auf Unverständnis und Unwillen, wenn sie gezwungen werden, damit zu arbeiten.

    Gut, dies muss ich jetzt einsehen 🙂



  • wo steht das eigentlich, dass die include-Guards nicht mit "__" beginnen dürfen? das ist mir bis dato neu und hat auch noch nie probleme gemacht, weder bei MSVC++ noch bei C::B -> GNU-GCC, auf das ich grade umsteige.



  • FreakyBKA schrieb:

    wo steht das eigentlich, dass die include-Guards nicht mit "__" beginnen dürfen?

    Im C++-Standard. Ich suchs dir jetzt nicht raus, aber wenn du dich im Forum (und in den FAQ) ein wenig umschaust, findest du sicher entsprechende Paragraphen.

    FreakyBKA schrieb:

    das ist mir bis dato neu und hat auch noch nie probleme gemacht, weder bei MSVC++ noch bei C::B -> GNU-GCC, auf das ich grade umsteige.

    Na das ist aber ein Argument.


Anmelden zum Antworten