Lowlevel

Lowlevel => OS-Design => Thema gestartet von: nnosdev am 15. February 2012, 21:55

Titel: C oder C++
Beitrag von: nnosdev am 15. February 2012, 21:55
Lasst mal was hören Leute ^^

Ich persönlich steh ja absolut auf die Möglichkeit objektorientiert zu programmieren.

Gibts ein paar Tipps bzw Ratschläge die einem helfen können für welche Sprache
man sich konkret entscheidet?

:)
Titel: Re: C oder C++
Beitrag von: XanClic am 16. February 2012, 02:09
Erstmal ist das ja sowieso eine Glaubensfrage. Wenn du C++ willst, dann solltest du den Kernel auch in C++ programmieren. So einfach ist das.

Um auch noch mehr Senf loszuwerden, könnte ich noch anbieten, dass man in C nichtsdestotrotz auch objektorientiert programmieren kann – die Frage ist dann nur, ob man das will, mit Funktionspointern für Methoden, ohne impliziten this-Pointer und ohne so aparte¹ Sachen wie Konstrukturaufrufen mit new und Destruktoraufrufen mit delete. Ansonsten kenne ich mich vermutlich nicht genug mit C++ aus, um zu wissen, was man sonst noch so haben können wöllte (Überladung sollte man inzwischen in C auch mit einer kräftigen Prise Präprozessormagie hinbekommen). Aber das nur, weil das meiner Meinung nach in jede Diskussion um C vs. C++ gehört.

Und zuletzt gehört in so eine Diskussion, dass C++ längst keine Obermenge mehr von C ist. Seit C99 und jetzt zusätzlich mit C11 gibt es in C Features, die es in C++ nicht gibt (v. a. wären da für mich Arrays variabler Länge zu nennen, sind aber noch einige andere). Wenn du die aber eh nicht nutzt, dann kannst du mit C++ wohl zumindest wenig falsch machen, denke ich.


¹ Das hat mir dict.leo.org als Übersetzung für „fancy“ angeboten, weil mir selbst kein apartes deutsches Wort dafür eingefallen ist. Ich wäre ja für die Einführung des Wortes fehnzig.
Titel: Re: C oder C++
Beitrag von: LittleFox am 16. February 2012, 09:37
Hi,

meiner Meinung nach geht C++ im Kernel richtig gut. Nur Exceptions und RTTI bekommt man nur mit viel Aufwand hin.
Außerdem brauchst du für einige Features erstmal eine kleine Runtime Library, die auf einige Kernelfeatures aufbaut - bspw. new und delete die auf deiner Speicherverwaltung aufbauen.

Grüße,
LittleFox
Titel: Re: C oder C++
Beitrag von: kevin am 16. February 2012, 10:51
Eigentlich sollte man so einen Thread ja sofort abschließen und den Autor für eine Woche sperren, aber wir hatten schon lange keinen anständigen Flamewar mehr. Wird vielleicht Zeit...

Ich persönlich steh ja absolut auf die Möglichkeit objektorientiert zu programmieren.
Geht mit C wunderbar. :)

Zitat
Gibts ein paar Tipps bzw Ratschläge die einem helfen können für welche Sprache man sich konkret entscheidet?
Man überlegt sich, ob man { oder begin schöner findet und nimmt dann entweder C oder ObjFPC.

Erstmal ist das ja sowieso eine Glaubensfrage. Wenn du C++ willst, dann solltest du den Kernel auch in C++ programmieren. So einfach ist das.
Und hinterher keinem anderen die Schuld dafür geben.

Zitat
Um auch noch mehr Senf loszuwerden, könnte ich noch anbieten, dass man in C nichtsdestotrotz auch objektorientiert programmieren kann – die Frage ist dann nur, ob man das will, mit Funktionspointern für Methoden, ohne impliziten this-Pointer und ohne so aparte¹ Sachen wie Konstrukturaufrufen mit new und Destruktoraufrufen mit delete.
Präprozessor to the rescue?  :-D

Zitat
(Überladung sollte man inzwischen in C auch mit einer kräftigen Prise Präprozessormagie hinbekommen).
Hm, du meinst, mit diesem C11-Union-Parameter-Dingsda-Zeug? Würde ich gern mal in Code sehen, wenn du sowas gebastelt hast.

Zitat
Und zuletzt gehört in so eine Diskussion, dass C++ längst keine Obermenge mehr von C ist. Seit C99 und jetzt zusätzlich mit C11 gibt es in C Features, die es in C++ nicht gibt (v. a. wären da für mich Arrays variabler Länge zu nennen, sind aber noch einige andere). Wenn du die aber eh nicht nutzt, dann kannst du mit C++ wohl zumindest wenig falsch machen, denke ich.
Ui, dass C++ keine Arrays variabler Länge kann, war mir gar nicht bewusst. Die benutze ich ständig.

Das Totschlagargument hier ist ja mittlerweile mit C++11 behoben - es gibt endlich ein long long.

Ansonsten finde ich natürlich Designated Initializers und Compound Literals einen wesentlich Vorteil von C. Außerdem kann C++, wenn ich das richtig sehe, keine anonymen unions und structs.

Zitat
¹ Das hat mir dict.leo.org als Übersetzung für „fancy“ angeboten, weil mir selbst kein apartes deutsches Wort dafür eingefallen ist. Ich wäre ja für die Einführung des Wortes fehnzig.
"schick" hätte ja auch ganz gut gepasst, aber wenn schon, dass bin ich für "fänzig". Wobei mich dieser ganze Eindeutschungsversuch an "happig" für "happy" erinnert. ;)
Titel: Re: C oder C++
Beitrag von: XanClic am 16. February 2012, 21:49
Zitat
(Überladung sollte man inzwischen in C auch mit einer kräftigen Prise Präprozessormagie hinbekommen).
Hm, du meinst, mit diesem C11-Union-Parameter-Dingsda-Zeug? Würde ich gern mal in Code sehen, wenn du sowas gebastelt hast.
Sowas hab nicht ich gebaut. :-D

Irgendwann hab ich mal in den Tiefen des Internets Code gesehen, um Funktionen mit verschiedener Parameteranzahl per CPP zu überladen – mit den _Generic-Sachen sollte das nun auch für verschiedene Parametertypen funktionieren. Aus dem Stegreif hätte ich da also nichts parat.

Zitat
Und zuletzt gehört in so eine Diskussion, dass C++ längst keine Obermenge mehr von C ist. Seit C99 und jetzt zusätzlich mit C11 gibt es in C Features, die es in C++ nicht gibt (v. a. wären da für mich Arrays variabler Länge zu nennen, sind aber noch einige andere). Wenn du die aber eh nicht nutzt, dann kannst du mit C++ wohl zumindest wenig falsch machen, denke ich.
Ui, dass C++ keine Arrays variabler Länge kann, war mir gar nicht bewusst. Die benutze ich ständig.
Tjo, in gnu++ sind die auch drin, aber im ISO-C++ afaik nicht.
Titel: Re: C oder C++
Beitrag von: nnosdev am 16. February 2012, 21:57
Ich persönlich steh ja absolut auf die Möglichkeit objektorientiert zu programmieren.
Geht mit C wunderbar. :)

Mir ist schon klar, dass man mit C objektorientiert programmieren kann. Aber in diesem Falle fällt die
Wahl dann wohl auf C++ da sie ja nicht nur so tut als Dinge einen Zusammenhang hätten wogegen
man in C schon mehr Aufwand betreiben muss um sauber objektorientiert zu programmieren.

Erstmal ist das ja sowieso eine Glaubensfrage. Wenn du C++ willst, dann solltest du den Kernel auch in C++ programmieren. So einfach ist das.
Und hinterher keinem anderen die Schuld dafür geben.

Also hältst du C++ eher für die falsche Wahl? :)

Zitat
Um auch noch mehr Senf loszuwerden, könnte ich noch anbieten, dass man in C nichtsdestotrotz auch objektorientiert programmieren kann – die Frage ist dann nur, ob man das will, mit Funktionspointern für Methoden, ohne impliziten this-Pointer und ohne so aparte¹ Sachen wie Konstrukturaufrufen mit new und Destruktoraufrufen mit delete.
Präprozessor to the rescue?  :-D

Eben das wäre mir zu umständlich. Dann doch lieber C++


Warum benützen wir nicht ganz normal das Wort fancy? Wir sagen doch auch "Manager" und nicht "Leiter" ^
Titel: Re: C oder C++
Beitrag von: kevin am 17. February 2012, 10:01
Mir ist schon klar, dass man mit C objektorientiert programmieren kann. Aber in diesem Falle fällt die
Wahl dann wohl auf C++ da sie ja nicht nur so tut als Dinge einen Zusammenhang hätten wogegen
man in C schon mehr Aufwand betreiben muss um sauber objektorientiert zu programmieren.
Kommt darauf an, was du unter sauber verstehst und was du vorhast. Manche Konstrukte können in C umständlich werden, aber ich behaupte einfach mal, dass man die in der Regel auch nicht braucht.

Wo es allerdings in Sachen "so tun, als gäbe es einen Zusammenhang" (was auch immer du damit meinst) einen Unterschied zwischen C und C++ geben sollte, kann ich im Moment nicht nachvollziehen.

Zitat
Zitat
Um auch noch mehr Senf loszuwerden, könnte ich noch anbieten, dass man in C nichtsdestotrotz auch objektorientiert programmieren kann – die Frage ist dann nur, ob man das will, mit Funktionspointern für Methoden, ohne impliziten this-Pointer und ohne so aparte¹ Sachen wie Konstrukturaufrufen mit new und Destruktoraufrufen mit delete.
Präprozessor to the rescue?  :-D
Eben das wäre mir zu umständlich. Dann doch lieber C++
Das war nicht ernstgemeint. Ich würde den Präprozessor für diese Sachen nicht benutzen. Impliziter this-Pointer, new und delete sind Syntaxdetails. Mein C-Code muss nicht wie C++-Code aussehen. Ich kann den this-Pointer einfach explizit mitgeben und direkt Konstruktor und Destruktor statt new aufrufen.

Zitat
Warum benützen wir nicht ganz normal das Wort fancy? Wir sagen doch auch "Manager" und nicht "Leiter" ^
Tun wir das? Du gehörst wohl auch zu den Leuten, die Laptop statt Klapprechner sagen? ;)
Titel: Re: C oder C++
Beitrag von: nnosdev am 17. February 2012, 12:59
Wo es allerdings in Sachen "so tun, als gäbe es einen Zusammenhang" (was auch immer du damit meinst) einen Unterschied zwischen C und C++ geben sollte, kann ich im Moment nicht nachvollziehen.
Damit ist Code wie dieser gemeint ^^
typedef struct
{
    int anzahlRaeder;
    char* hupTon;
    int geschwindigkeit;
}Auto;

void Auto_init(Auto *this, int anzahlRaeder, char* hupTon);
void Auto_fahre(Auto *this);
void Auto_hupe(Auto *this, int anzahl);

oder dieser..

typedef struct
{
    Auto* pAuto;
}Garage;

void Garage_init(Garage *this);
void Garage_init2(Garage *this, Auto *pAuto);
void Garage_einparken(Garage *this, Auto *pAuto);
void Garage_ausparken(Garage *this);

Zitat
Zitat
Um auch noch mehr Senf loszuwerden, könnte ich noch anbieten, dass man in C nichtsdestotrotz auch objektorientiert programmieren kann – die Frage ist dann nur, ob man das will, mit Funktionspointern für Methoden, ohne impliziten this-Pointer und ohne so aparte¹ Sachen wie Konstrukturaufrufen mit new und Destruktoraufrufen mit delete.
Präprozessor to the rescue?  :-D
Eben das wäre mir zu umständlich. Dann doch lieber C++
Das war nicht ernstgemeint. Ich würde den Präprozessor für diese Sachen nicht benutzen. Impliziter this-Pointer, new und delete sind Syntaxdetails. Mein C-Code muss nicht wie C++-Code aussehen. Ich kann den this-Pointer einfach explizit mitgeben und direkt Konstruktor und Destruktor statt new aufrufen.
Nun aber genau bietet C++ eben den Komfort von impliziten this-Pointern um die man sich nicht kümmern muss bzw.
der automatisierte Aufruf des Destructors bei lokalen Objekten die man in C "von Hand" zerstören müsste, oder?

Zitat
Warum benützen wir nicht ganz normal das Wort fancy? Wir sagen doch auch "Manager" und nicht "Leiter" ^
Tun wir das? Du gehörst wohl auch zu den Leuten, die Laptop statt Klapprechner sagen? ;)
Du hast mich erwischt :D Klapprechner ist auch gut ^^
Titel: Re: C oder C++
Beitrag von: kevin am 17. February 2012, 13:29
Wo es allerdings in Sachen "so tun, als gäbe es einen Zusammenhang" (was auch immer du damit meinst) einen Unterschied zwischen C und C++ geben sollte, kann ich im Moment nicht nachvollziehen.
Damit ist Code wie dieser gemeint ^^
[...]
Okay, und wo wird da jetzt ein nicht vorhandener Zusammenhang vorgetäuscht, was außerdem auch noch in C++ nicht der Fall wäre?

Zitat
Nun aber genau bietet C++ eben den Komfort von impliziten this-Pointern um die man sich nicht kümmern muss bzw.
der automatisierte Aufruf des Destructors bei lokalen Objekten die man in C "von Hand" zerstören müsste, oder?
Implizite this-Pointer sind ein Komfortfeature, genau. Ob ich sie jetzt hinschreibe oder nicht macht meine Entwicklung nicht wesentlich einfacher oder schwieriger. Über solche Sachen muss ich mir keine großen Gedanken machen, und damit sie sind nebensächlich.

Dass Destruktoren von Hand aufgerufen werden müssen, ist m.E. kein Bug, sondern ein Feature. Damit sieht man im Code genau den Ablauf von oben nach unten und es passiert nicht noch implizit irgendwelche Magie, die man übersehen könnte, oder von der man wissen müsste, in welcher Reihenfolge sie ausgeführt wird.
Titel: Re: C oder C++
Beitrag von: DerHartmut am 17. February 2012, 13:53
Um ehrlich zu sein ist dieser ganze fetzige (meine deutsche Interpretation von "fancy") Hype um "Objektorientierung" eh nicht von allzulange Dauer - es wurde bewiesen, dass objektorientierte Programme inperformanter und fehleranfählliger sind und dazu neigen zu organisiert zu sein.

Für die Betriebssystementwicklung würde ich eher Assembler benutzen - C ist viel zu langsam und der gcc erzeugt sehr schlechten Assembler-Code, ein Mensch kann hier weitaus besser per Hand optimieren und alles (und damit meine ich wirklich alles) aus der Hardware herausholen was nur irgendwie geht. Auch die sehr komplizierte und fehleranfällige Syntax von C (die sich bis nach C++ durchzieht und dort durch die Objektorientierung noch komplizierter und fehleranfälliger wurde) machen es - gepaart mit dem schlechten Assembler-Code, der produziert wird - meiner Meinung nach nicht sehr empfehlenswert.

Wenn du aber dennoch Objektorientierung willst (wie gesagt, ich rate davon ab - macht das System nur unnötig komplex und überladen) solltest du dann schon C nehmen (ist halt nicht ganz so komplex wie C++) und den daraus produzierten Code per Hand nachoptimieren und ggf. wenn du über die Kenntnisse verfügst, ein Assembler-Programm schreiben, welches diese Optimierung übernimmt.
Titel: Re: C oder C++
Beitrag von: Jidder am 17. February 2012, 14:29
Vorsicht vor dem Troll! Und DemHartmut ist auch nicht zu trauen.
Titel: Re: C oder C++
Beitrag von: Paprikachu am 17. February 2012, 15:16
Dass Destruktoren von Hand aufgerufen werden müssen, ist m.E. kein Bug, sondern ein Feature. Damit sieht man im Code genau den Ablauf von oben nach unten und es passiert nicht noch implizit irgendwelche Magie, die man übersehen könnte, oder von der man wissen müsste, in welcher Reihenfolge sie ausgeführt wird.
C hat ein Problem (nicht): Exceptions. Durch Exceptions entsteht das Problem, dass Routinen zur Freigabe von Resourcen beim Verlassen des Scopes durch eine solche nicht aufgerufen werden. Dieses Problem ist mit RAII in C++ sehr elegangt gelöst.
Das kleinere Problem, welches übrigens auch noch in C vorhanden ist, ist, dass man auf den Aufruf einer Freigabe-Funktion vergessen könnte. Auch das kann in C++ mit RAII nicht passieren.

Was du mit der Magie-Aussage sagen willst, verstehe ich nicht. Da gibt es weder was zu übersehen, noch interessiert da die Reihenfolge. (Die im C++-Standard übrigens exakt festgelegt ist.)
Titel: Re: C oder C++
Beitrag von: kevin am 17. February 2012, 15:25
Ich glaube nicht, dass Exceptions wirklich viel ändern. In C hast du stattdessen eben ein goto dastehen, aber gemeinsam haben beide Methoden, dass du irgendwo mittendrin rausspringst. In C hat man halt am Ende irgendein fail:-Label. Genauso kann man in Sprachen mit Exceptions am Funktionsende die Exception fangen, Zeug freigeben und weiterwerfen. In manchen Sprachen wie C++ wäre das syntaktisch nicht so schön, aber das liegt nicht am Konzept.

Was die Reihenfolge angeht, kann ich mir gut vorstellen, dass das definiert ist, aber kennt diese Definition auch jeder?
Titel: Re: C oder C++
Beitrag von: Paprikachu am 17. February 2012, 15:48
Ich glaube nicht, dass Exceptions wirklich viel ändern. In C hast du stattdessen eben ein goto dastehen, aber gemeinsam haben beide Methoden, dass du irgendwo mittendrin rausspringst. In C hat man halt am Ende irgendein fail:-Label.
Der Unterschied ist: Mit Exceptions muss ich keinen extra Code für die Fehlerbehandlung in Funktionen schreiben, die den Fehler gar nicht behandeln.
Außerdem: Warum willst du einem Objekt explizit sagen müssen, dass es sich aufräumen soll? Wenn es zerstört wird (Sei es automatisch durch verlassen des Scopes, oder durch eine Deallokation über free()/delete), ist die einzig logische Konsequenz, dass Resourcen mitaufgeräumt werden. Warum das also nicht automatisieren?

Genauso kann man in Sprachen mit Exceptions am Funktionsende die Exception fangen, Zeug freigeben und weiterwerfen. In manchen Sprachen wie C++ wäre das syntaktisch nicht so schön, aber das liegt nicht am Konzept.
Au ja. Das führt dann zu tollen try/catch/finally-Konstruktionen. Ein kleines Beispiel in Java:
try
{
    mystream.read();
}

finally
{
    try { mystream.close(); } catch(IOException e) {}
}
Oder das ganze nochmal auf C++ übertragen (Wir nehmen für einen kurzen Moment an, es gäbe kein RAII):
// Exceptions wurden vorher am Stream eingeschaltet

try
{
    char c;
    mystream.read(&c, sizeof c);
}

catch(...)
{
    mystream.close();
    throw;
}
Willst du echt sowas schreiben müssen?

Was die Reihenfolge angeht, kann ich mir gut vorstellen, dass das definiert ist, aber kennt diese Definition auch jeder?
Die Reihenfolge ist für den Benutzer irrelephant. Aber ich kann dich beruhigen: Die Reihenfolge ist so intuitiv, wie man sich nur denken kann: Umgekehrt zur Reihenfolge der Erzeugung. Und spätestens, wenn man Variablen hat, die voneinander abhängen (Zeiger/Referenzen aufeinander halten), kann das nur die einzige Möglichkeit sein.
Und wenn dich das immer noch nicht überzeugt: Du musst auch lernen, wie man Variablen benutzt, wie man Funktionen schreibt und dass der Returnwert der Main-Funktion nicht void ist. Sowas gehört zu den Sprachgrundlagen.
Titel: Re: C oder C++
Beitrag von: kevin am 17. February 2012, 16:23
Der Unterschied ist: Mit Exceptions muss ich keinen extra Code für die Fehlerbehandlung in Funktionen schreiben, die den Fehler gar nicht behandeln.
Außerdem: Warum willst du einem Objekt explizit sagen müssen, dass es sich aufräumen soll? Wenn es zerstört wird (Sei es automatisch durch verlassen des Scopes, oder durch eine Deallokation über free()/delete), ist die einzig logische Konsequenz, dass Resourcen mitaufgeräumt werden. Warum das also nicht automatisieren?
Um im Code genau zu sehen, wann was passiert. Meinetwegen kannst du das in einer hypothetischen Sprache sogar so machen, dass es einen Compilerfehler gibt, wenn ich das Objekt nicht aufräume, aber ich will, dass explizit dasteht, was gemacht wird.

Zitat
Au ja. Das führt dann zu tollen try/catch/finally-Konstruktionen. Ein kleines Beispiel in Java:
Wie gesagt, die Syntax in C++ ist nicht so toll dafür. Zum Beispiel mit Ada sähe das so aus (schnell aus dem Internet zusammenkopiert, weil ich es lang nicht mehr benutzt habe und mit Dateien wohl eh nie was gemacht habe):
procedure foo is
    file: File_Type;
    c: Character;
begin
    Open(File => file, Name => "/usr/local/widgets/data", Mode => In_File);
    Get (file, c);
    Close(file);
exception
    when Error: others =>
        Close(file);
end foo;

Das kriegt man sich auch nochmal etwas netter formatiert, aber grundsätzlich bist du da syntaktisch schon wieder recht nahe an der expliziten, aber trotzdem übersichtlichen C-Version (da ist halt ein zusätzliches if drin, was auch wieder den möglichen Ablauf genauer klarmacht, aber das könnte man in der hypothetischen Sprache sicher auch noch ein bisschen Syntactic Sugar verpassen):
int foo(void)
{
    FILE* f = fopen(...);
    ret = do_something(f);
    if (ret < 0) {
        goto fail;
    }

    ret = 0;
fail:
    fclose(f);
    return ret;
}

Zitat
Die Reihenfolge ist für den Benutzer irrelephant. Aber ich kann dich beruhigen: Die Reihenfolge ist so intuitiv, wie man sich nur denken kann: Umgekehrt zur Reihenfolge der Erzeugung. Und spätestens, wenn man Variablen hat, die voneinander abhängen (Zeiger/Referenzen aufeinander halten), kann das nur die einzige Möglichkeit sein.
Und Zeiger/Referenzen können nur im Konstruktor gesetzt werden und nicht irgendwann in der Mitte der Lebenszeit des Objekts? Für mich klingt das nach einem Rezept für subtile Fehler.

Zitat
Und wenn dich das immer noch nicht überzeugt: Du musst auch lernen, wie man Variablen benutzt, wie man Funktionen schreibt und dass der Returnwert der Main-Funktion nicht void ist. Sowas gehört zu den Sprachgrundlagen.
Ich muss es lernen, wenn ich diese Sprache benutzen will. Aber ich muss es nicht gut finden und ich kann beschließen, dass ich die Sprache deswegen nicht benutzen will (wenn es der einzige Grund wäre, wäre das vermutlich ein eher schwaches Argument, aber es trägt dazu bei).
Titel: Re: C oder C++
Beitrag von: Sannaj am 17. February 2012, 16:25
Man sollte sich schon zwischen C und C++ entscheiden. C nehmen und dann die Objektorientierung per CPP versuchen nachzuäffen halte ich für wenig ratsam.

Für den Kernel würde ich persönlich C nehmen.
C++ bietet zwar die OOP, der wichtigste Hebel für die Verwendung der OOP, nämlich die GUI-Elemente, sowie die meisten anderen Vorteile der OOP (Dateizugriff, Agenten, etc.) fallen im Lowlevel Bereich weg. (OOP ist immer dann stark, wenn man viele Dingen hat, die sich nur in Details oder nur in Parametern unterscheiden, und auf die verschiedene Aktionen angewand werden können. Mir fallen da in Bezug auf Betriebssysteme eigentlich nur Tasks ein.) Im Lowlevelsektor fallen mir da spontan nur Darüber hinaus, passieren bei der OOP sehr viele Dinge auch implizit und nicht unbedingt vorhersehbar, was bei der Lowlevel Programmierung nicht unbedingt von Vorteil ist.

Ein weiterer Schwachpunkt von C ist das Fehlen von überladbaren Methoden, das bei der Lowlevelprogrammierung aber auch nicht so zu Geltung kommt. (Der Kernel ist ja keine Mathesoftware, die generische sin(), cos() etc. Funktionen braucht.). Auch dynamische Strukturen sind im Kernel recht unbrauchbar. Präprozessormagie zum lösen des Überladeproblems ist übrigens nicht implementierungsunabhängig, oder extrem aufwendig: http://carolina.mff.cuni.cz/~trmac/blog/2005/the-ugliest-c-feature-tgmathh/
Titel: Re: C oder C++
Beitrag von: Paprikachu am 17. February 2012, 17:06
Um im Code genau zu sehen, wann was passiert. [...], aber ich will, dass explizit dasteht, was gemacht wird.
Das verstehe ich nicht. Warum willst du das wissen? Wie genau sich das Objekt aufräumt, ist ein Implementierungsdetail, und dass es aufgeräumt wird, garantiert dir der Standard. Wozu willst du das sehen/hinschreiben müssen? Für mich ist das etwas logisch schon implizites, eine Selbstverständlichkeit. Ich würde mich wundern, das hinschreiben zu müssen. Offenbar ist diese Logik noch nicht zu anderen "modernen" OOP-Sprachen durchgedrungen.

Meinetwegen kannst du das in einer hypothetischen Sprache sogar so machen, dass es einen Compilerfehler gibt, wenn ich das Objekt nicht aufräume
Bei Stackobjekten: Okay. Aber wie willst du das bei Objekten am Heap bzw Zeigern auf Objekte lösen? Der Compiler kann nicht wissen, welche Lebenszeit das Ding haben soll. Es kann sogar vorkommen, dass du selbst es nicht weißt, weil es z.B. von äußeren Umständen, wie Spielern auf einem Server abhängt.

Wie gesagt, die Syntax in C++ ist nicht so toll dafür. Zum Beispiel mit Ada sähe das so aus (schnell aus dem Internet zusammenkopiert, weil ich es lang nicht mehr benutzt habe und mit Dateien wohl eh nie was gemacht habe):
[...]
Okay, das ist immerhin schon besser. Aber ich bezweifle, dass diese Fehlerbehandlung in Ada so mächtig ist, wie ein try in anderen Sprachen (Ich kann Ada nicht.). Kann ich damit z.B. nur Fehler in den Zeilen X und Y fangen? Trotzdem: Auch hier kann ich das Freigeben vergessen.

Das kriegt man sich auch nochmal etwas netter formatiert, aber grundsätzlich bist du da syntaktisch schon wieder recht nahe an der expliziten, aber trotzdem übersichtlichen C-Version (da ist halt ein zusätzliches if drin, was auch wieder den möglichen Ablauf genauer klarmacht, aber das könnte man in der hypothetischen Sprache sicher auch noch ein bisschen Syntactic Sugar verpassen):
[...]
Da hier nur eine Resource im Spiel ist, ist alles noch relativ einfach. Sobald es aber mehrere werden, gibts für jede Überprüfung ein if, nur damit der richtige Returncode zurückgegeben wird. Exceptions sind um Welten eleganter, einfacherer und sicherer zu verwenden. (Vorausgesetzt, man hat RAII.)

Und Zeiger/Referenzen können nur im Konstruktor gesetzt werden und nicht irgendwann in der Mitte der Lebenszeit des Objekts? Für mich klingt das nach einem Rezept für subtile Fehler.
Was du mir damit sagen willst, verstehe ich nicht. Es ist ganz natürlich, dass Objekte voneinander abhängen. Indem man die Objekte umgekehrt zu ihrer Erzeugungsreihenfolge zerstört, kann eben nichts schief gehen.

Ich muss es lernen, wenn ich diese Sprache benutzen will.
Jeder Sprache hat ihre Eigenheiten. Außerdem ist das nicht wirklich eine Regel, die viel Lernen bedarf. Meiner Meinung nach ist das eines der logischsten Dinge überhaupt, die man eigentlich gar nicht nachsehen muss.
Titel: Re: C oder C++
Beitrag von: kevin am 17. February 2012, 17:09
C++ bietet zwar die OOP, der wichtigste Hebel für die Verwendung der OOP, nämlich die GUI-Elemente, sowie die meisten anderen Vorteile der OOP (Dateizugriff, Agenten, etc.) fallen im Lowlevel Bereich weg. (OOP ist immer dann stark, wenn man viele Dingen hat, die sich nur in Details oder nur in Parametern unterscheiden, und auf die verschiedene Aktionen angewand werden können. Mir fallen da in Bezug auf Betriebssysteme eigentlich nur Tasks ein.) Im Lowlevelsektor fallen mir da spontan nur Darüber hinaus, passieren bei der OOP sehr viele Dinge auch implizit und nicht unbedingt vorhersehbar, was bei der Lowlevel Programmierung nicht unbedingt von Vorteil ist.
Es gibt in einem OS schon recht viele Sachen, wo es sinnvoll ist, objektorientiert ranzugehen. Aber sie brauchen in der Regel keine größere Magie von der Programmiersprache, sondern oft z.B. nur unterschiedliche Implementierungen eines Interfaces. Manchmal noch ein bisschen Vererbung, aber meistens nicht.

Dateien sind zum Beispiel eindeutig ein Objekt. Ihre Implementierung unterscheidet sich je nachdem, ob sie auf ext2, FAT oder in einer Ramdisk liegen. Aber um das umzusetzen brauche ich nur pro FS-Treiber ein const struct von Funktionspointern und keine großartige C++-Magie.

Zitat
Ein weiterer Schwachpunkt von C ist das Fehlen von überladbaren Methoden, das bei der Lowlevelprogrammierung aber auch nicht so zu Geltung kommt. (Der Kernel ist ja keine Mathesoftware, die generische sin(), cos() etc. Funktionen braucht.).
Mit _Generic geht das wohl in C11 so einigermaßen. Obwohl ich jetzt einfach mal sage, einen Schönheitswettbewerb gewinnt das nicht.

Womit auch das Stichwort für das eine wirklich fehlende Feature in C gegeben ist: Richtige Generics. Also der Teil von Templates, den man wirklich braucht. Auf das Berechnung von Primzahlen zur Compilezeit verzichte ich gern. ;)
Titel: Re: C oder C++
Beitrag von: Paprikachu am 17. February 2012, 17:16
Womit auch das Stichwort für das eine wirklich fehlende Feature in C gegeben ist: Richtige Generics. Also der Teil von Templates, den man wirklich braucht. Auf das Berechnung von Primzahlen zur Compilezeit verzichte ich gern. ;)
Nur weil du sowas mit diesen Features machen kannst, heißt das nicht, dass diese schlecht sind. Im Übrigen hat C++11 dafür jetzt sowieso ein neues Sprachfeature, constexpr.
Titel: Re: C oder C++
Beitrag von: kevin am 17. February 2012, 17:39
Das verstehe ich nicht. Warum willst du das wissen? Wie genau sich das Objekt aufräumt, ist ein Implementierungsdetail, und dass es aufgeräumt wird, garantiert dir der Standard. Wozu willst du das sehen/hinschreiben müssen? Für mich ist das etwas logisch schon implizites, eine Selbstverständlichkeit. Ich würde mich wundern, das hinschreiben zu müssen. Offenbar ist diese Logik noch nicht zu anderen "modernen" OOP-Sprachen durchgedrungen.
Damit ich daran erinnert werde, dass hier was passiert. Dass ich auf einen Blick die möglichen Codepfade sehen kann. Ohne den Code zu kennen und ohne zu wissen, welche anderen Klassen Destruktoren haben.

Zitat
Bei Stackobjekten: Okay. Aber wie willst du das bei Objekten am Heap bzw Zeigern auf Objekte lösen? Der Compiler kann nicht wissen, welche Lebenszeit das Ding haben soll. Es kann sogar vorkommen, dass du selbst es nicht weißt, weil es z.B. von äußeren Umständen, wie Spielern auf einem Server abhängt.
Das löse ich so wie in C++: Für alles, was auf dem Heap ist, wird keine Freigabe erzwungen.

Zitat
Okay, das ist immerhin schon besser. Aber ich bezweifle, dass diese Fehlerbehandlung in Ada so mächtig ist, wie ein try in anderen Sprachen (Ich kann Ada nicht.). Kann ich damit z.B. nur Fehler in den Zeilen X und Y fangen? Trotzdem: Auch hier kann ich das Freigeben vergessen.
Naja, du kannst überall einen begin-end-Block anfangen, damit geht es dann wieder stark in Richtugn eines try-catch.

Und ja, ich gebe ja zu, dass vergessen lassen nicht gut ist. Aber das bekämpft man am besten nicht mit automagischem Fixen, sondern mit Compilerfehlern, wenn man es vergisst.

Zitat
Da hier nur eine Resource im Spiel ist, ist alles noch relativ einfach. Sobald es aber mehrere werden, gibts für jede Überprüfung ein if, nur damit der richtige Returncode zurückgegeben wird. Exceptions sind um Welten eleganter, einfacherer und sicherer zu verwenden. (Vorausgesetzt, man hat RAII.)
Wenn im Lauf der Funkion mehrere Sachen angelegt werden, die freigegeben werden müssen, gibt es mehrere verschiedene Labels, ja. So what?

Zitat
Und Zeiger/Referenzen können nur im Konstruktor gesetzt werden und nicht irgendwann in der Mitte der Lebenszeit des Objekts? Für mich klingt das nach einem Rezept für subtile Fehler.
Was du mir damit sagen willst, verstehe ich nicht. Es ist ganz natürlich, dass Objekte voneinander abhängen. Indem man die Objekte umgekehrt zu ihrer Erzeugungsreihenfolge zerstört, kann eben nichts schief gehen.
Hab mal ein bisschen damit rumgespielt (verzeih mir mein C++, ich würde das normal nicht tun):
#include <iostream>

using namespace std;

class Foo {
    public:
        int x;
        Foo* other_foo;
        Foo* nochn_foo;

        Foo(int x);
        ~Foo();
};

Foo::Foo(int x) : x(x), other_foo(0), nochn_foo(0)
{
}

Foo::~Foo()
{
    cout << x << endl;

    if (other_foo != NULL) {
        cout << "other_foo: " << other_foo->nochn_foo->x << endl;
    }

    if (nochn_foo) {
        delete nochn_foo;
    }
}

int main(void)
{
    Foo foo(2);
    Foo bar(42);

    bar.nochn_foo = new Foo(1337);
    foo.other_foo = &bar;

    return 0;
}

Das gleiche Ziel kann man wahrscheinlich auch einfacher erreichen, aber dass dieses Muster so mal in einem komplexeren Programm auftritt halte ich für gar nicht unwahrscheinlich. Ist natürlich Mist, wie valgrind richtig erkennt:
==16813== Invalid read of size 4
==16813==    at 0x4009D7: Foo::~Foo() (in /tmp/c/a.out)
==16813==    by 0x400A9D: main (in /tmp/c/a.out)
==16813==  Address 0x4c3b040 is 0 bytes inside a block of size 24 free'd
==16813==    at 0x4A0528C: operator delete(void*) (vg_replace_malloc.c:387)
==16813==    by 0x400A28: Foo::~Foo() (in /tmp/c/a.out)
==16813==    by 0x400A91: main (in /tmp/c/a.out)
Titel: Re: C oder C++
Beitrag von: Paprikachu am 17. February 2012, 18:28
Damit ich daran erinnert werde, dass hier was passiert. Dass ich auf einen Blick die möglichen Codepfade sehen kann. Ohne den Code zu kennen und ohne zu wissen, welche anderen Klassen Destruktoren haben.
Ich weiß, meiner Fragerei ist unglaublich nervig, aber es will mir nicht einleuchten. Warum willst du daran erinnert werden, dass da was passiert? Warum willst du auf einen Blick alle möglichen Codepfade sehen?
Du musst nicht wissen, welche anderen Klassen Destruktoren haben.

Hab mal ein bisschen damit rumgespielt (verzeih mir mein C++, ich würde das normal nicht tun):
[...]
Und was soll das jetzt aussagen, außer dass der Programmierer (= du) einen Fehler gemacht hat? Davor kann dich keine Sprache beschützen.
Titel: Re: C oder C++
Beitrag von: kevin am 17. February 2012, 18:39
Ich weiß, meiner Fragerei ist unglaublich nervig, aber es will mir nicht einleuchten. Warum willst du daran erinnert werden, dass da was passiert? Warum willst du auf einen Blick alle möglichen Codepfade sehen?
Du musst nicht wissen, welche anderen Klassen Destruktoren haben.
Damit ich verstehe, was passiert, und nicht Code produziere, der nicht tut, weil die Destruktoren, an die ich nicht denken soll, irgendwelche Nebeneffekte haben?

Zitat
Und was soll das jetzt aussagen, außer dass der Programmierer (= du) einen Fehler gemacht hat? Davor kann dich keine Sprache beschützen.
Die Sprache hat mir gesagt: "Kümmer dich nicht um das Aufräumen, ich mach das". Sie hat damit erstens dafür gesorgt, dass ich nicht drauf aufmerksam werde, weil es implizit passiert, und mir zweitens die Möglichkeit weggenommen, selber in der richtigen Reihenfolge aufzuräumen. Andersrum aufräumen hätte in diesem Beispiel nämlich funktioniert.

Du hast gesagt "Indem man die Objekte umgekehrt zu ihrer Erzeugungsreihenfolge zerstört, kann eben nichts schief gehen." und plötzlich geht eben doch was schief, weil die Sprache meint, schlauer zu sein als der Programmierer.

Nur aus Neugier, wie würde man das richtig machen, wenn man solche Beziehungen hätte? Muss ich die Beziehung erst von Hand brechen bevor ich die Destruktoren laufen lassen kann?
Titel: Re: C oder C++
Beitrag von: Paprikachu am 17. February 2012, 19:21
Damit ich verstehe, was passiert, und nicht Code produziere, der nicht tut, weil die Destruktoren, an die ich nicht denken soll, irgendwelche Nebeneffekte haben?
Destruktoren haben üblicherweise keine Nebeneffekte, an die du denken sollst. In keiner gut designten Lib gibt es Dtoren, bei denen du dich um irgendwas kümmern musst.

Die Sprache hat mir gesagt: "Kümmer dich nicht um das Aufräumen, ich mach das". Sie hat damit erstens dafür gesorgt, dass ich nicht drauf aufmerksam werde, weil es implizit passiert, und mir zweitens die Möglichkeit weggenommen, selber in der richtigen Reihenfolge aufzuräumen. Andersrum aufräumen hätte in diesem Beispiel nämlich funktioniert.

Du hast gesagt "Indem man die Objekte umgekehrt zu ihrer Erzeugungsreihenfolge zerstört, kann eben nichts schief gehen." und plötzlich geht eben doch was schief, weil die Sprache meint, schlauer zu sein als der Programmierer.

Nur aus Neugier, wie würde man das richtig machen, wenn man solche Beziehungen hätte? Muss ich die Beziehung erst von Hand brechen bevor ich die Destruktoren laufen lassen kann?
Ach, jetzt verstehe ich das Problem erst. Ziemlich verzwickte Sache. Lösung: Überdenk dein Design, ich glaube nicht, dass das so irgendwie Sinn ergeben würde.
Titel: Re: C oder C++
Beitrag von: kevin am 17. February 2012, 19:35
Das sieht vielleicht konstruiert aus, aber ich glaube nicht, dass das abwegig ist, was ich mache. Ich habe zwei Objekte A und B auf dem Stack und ein Attribute von A  fängt irgendwann an, auf B zu verweisen. Ich vermute, das ist schon genug, damit bei der falschen Reihenfolge das Verhalten laut Standard undefiniert wird (nicht nachgelesen allerdings); in der Praxis hat es nicht gereicht, weil B - obwohl destruiert - immer noch auf dem Stack liegt. Deswegen habe ich in B intern noch ein Objekt C auf dem Heap eingeführt, das mit dem Destruktor definitiv ungültig wird.

Ich finde das alles ganz und gar nicht abwegig. C ist ein Implementierungsdetail von B. Der entscheidende Fehler, den das Programm macht, ist, dass es einem früher definierten Objekt ein später definiertes als Attribut zuweist. Dass das Vertauschen von Definitionen, die (bei der Initialisierung) nicht voneinander abhängen, ein Programm fixt, kann man logisch finden, wenn man unbedingt will. Muss man aber sicher nicht.
Titel: Re: C oder C++
Beitrag von: Sannaj am 17. February 2012, 20:30
Ein weiterer Schwachpunkt von C ist das Fehlen von überladbaren Methoden, das bei der Lowlevelprogrammierung aber auch nicht so zu Geltung kommt. (Der Kernel ist ja keine Mathesoftware, die generische sin(), cos() etc. Funktionen braucht.).
Mit _Generic geht das wohl in C11 so einigermaßen. Obwohl ich jetzt einfach mal sage, einen Schönheitswettbewerb gewinnt das nicht.

Naja, _Generic ist schon in Ordnung. Man kann ja #define generic _Generic oder so nutzten.
Zitat
Womit auch das Stichwort für das eine wirklich fehlende Feature in C gegeben ist: Richtige Generics. Also der Teil von Templates, den man wirklich braucht. Auf das Berechnung von Primzahlen zur Compilezeit verzichte ich gern. ;)
Generische Funktionen ließen sich sehr gut umsetzten, wenn man eine komfortable Makrofunktion einbaut. Allerdings nützten dir generische Funktion in C nicht so viel, weil du keine Operatoren überladen kannst.
Titel: Re: C oder C++
Beitrag von: LittleFox am 17. February 2012, 22:08
Hi,

sorry dass ich mich etwas OT einmische, aber das muss jetzt einfach sein ;)
@DerHartmut und sowas von jemanden der Perl programmiert???

Meine Meinung zu C++ hab ich ja bereits geschrieben.

Grüße,
LittleFox
Titel: Re: C oder C++
Beitrag von: MNemo am 18. February 2012, 00:03
Eigentlich sollte euch doch allen klar sein C++ kann gar nicht viel besser sein als C:
c == c++
Nur D ist wirklich besser. :-D (Ok. Bei anständigen Compilern hängt es noch.)
Titel: Re: C oder C++
Beitrag von: kevin am 18. February 2012, 00:05
Oh, der Ansatz gefällt mir: Je nach Auswertungsreihenfolge ist allenfalls C größer als C++. ;)
Titel: Re: C oder C++
Beitrag von: nnosdev am 19. February 2012, 14:52
Okay, also wirklich entscheiden kann ich mich jetzt nicht ^^

Persönlich tendiere ich nach wie vor eher zu C++ weil ich ganz einfach die Sprache "schöner" und nachvollziehbarer finde als C (ja, auch wenn man mit C dasselbe anstellen kann wie mit C++)

Eigentlich sollte euch doch allen klar sein C++ kann gar nicht viel besser sein als C:
c == c++

Das hängt u.A vom Compiler ab ob C==C++  :-D
Titel: Re: C oder C++
Beitrag von: bluecode am 23. February 2012, 20:32
Zwei Anmerkungen:
1. Was überhaupt nicht zu Sprache kam waren Templates für nettere Container ohne void* bzw. einmal bei der Implementierung castet man halt und nicht ständig. Ich finde, dass das Datenstrukturen allgemein um einiges angenehmer macht
2. Zur oben erwähnten RAII: Zwei weitere sehr relevante Beispiele ist std::shared_ptr für automagische Freigabe von Objekten (in meinen letzten Projekten hatte ich kein einziges delete mehr) und automatisches freigeben von Locks (das hatte ich auch mal so implementiert und fand es sehr hilfreich:
Mutex mymutex;
[...]
void f([...])
{
  // code außerhalb der critical section

  {
    scoped_lock l(mymutex); // <- ruft mymutex.lock() auf

    // code innerhalb des critical section
  } // <- exakt hier kommt der Destruktor von l und ruft mymutex.unlock() auf

  // code außerhalb des critical section
}
Das schöne daran ist, dass es schlichtweg egal ist wie man ans Ende des Blocks kommt, es wird immer der Lock freigegeben, ohne häßliches goto + rumgehacke um den return value irgendwie dann am Ende hinzukriegen.
Titel: Re: C oder C++
Beitrag von: nnosdev am 19. March 2012, 00:51
Okay, Templates sind sicherlich eine angenehme Sache. Aber jetzt auf die schnelle wüsste ich nichts
wo ich die tief im Kernel brauchen könnte. Scoped-Lock ist ein nettes Design-Pattern! Aber theoretisch liese sich das
einigermaßen simpel auch mit C realisieren.

Ich habe ein recht interessantes PDF (http://www.planetpdf.com/codecuts/pdfs/ooc.pdf) im Netz gefunden.
Auf Seite 18 bzw. 19 kann man recht schnell sehen wie sich so etwas machen liese.
Das dürfe ganz im Sinne von taljeth sein, oder? ^^
Titel: Re: C oder C++
Beitrag von: kevin am 19. March 2012, 13:09
Ich bin mir nicht so sicher, ob die Ansätze in diesem Dokument so toll sind, z.B. das new(const void* type, ...). Warum versucht man denn, verbissen irgendwas anderes schlecht zu imitieren anstatt C-Code zu schreiben? Was ist an new(Point, x, y) besser als an einem typsicheren new_point(x, y)?
Titel: Re: C oder C++
Beitrag von: nnosdev am 19. March 2012, 13:21
Naja einmal korrekt implementiert müsste man dann nie mehr ein neues "new_xyz()"
schreiben oder nicht? :)
Titel: Re: C oder C++
Beitrag von: kevin am 19. March 2012, 14:29
Ja, schon. Die Frage ist nur, inwieweit man bei void* und ... von korrekt sprechen kann. ;)

Typsicherheit ist zumindest für mich dann doch auch ein Kriterium.
Titel: Re: C oder C++
Beitrag von: nnosdev am 19. March 2012, 14:51
Aber ist man auf einer gewissen Ebene (nämlch auf einer sehr niedrigen) nicht irgendwo mal am Limit?
Es stellt sich die Frage, ob man an dieser Stelle wirklich auf Typensicherheit angewiesen ist.

new() soll ja jedes Objekt anlegen egal von welchen Typen. Da ist void* doch irgendwie passend, oder nicht?
Titel: Re: C oder C++
Beitrag von: XanClic am 19. March 2012, 16:37
Das kann man doch mit C11 bestimmt ganz toll machen, so ungefähr:
#define new(X, ...) *X = _Generic((*X), point: new_point)(__VA_ARGS__)
Titel: Re: C oder C++
Beitrag von: bluecode am 19. March 2012, 19:08
Okay, Templates sind sicherlich eine angenehme Sache. Aber jetzt auf die schnelle wüsste ich nichts wo ich die tief im Kernel brauchen könnte.
Wie gesagt: Datenstrukturen. Zumindest ich würde meinen Monitor gegen die Wand schmeißen wenn ich die jedes Mal wieder neu implementieren müsste oder auf die Krücke void* zurückfallen würde.

Zitat
Scoped-Lock ist ein nettes Design-Pattern! Aber theoretisch liese sich das einigermaßen simpel auch mit C realisieren.
Ich wüsste nicht wie man das in C nachmachen würde und schon gar nicht "simpel".
Titel: Re: C oder C++
Beitrag von: kevin am 19. March 2012, 22:24
Wie gesagt: Datenstrukturen. Zumindest ich würde meinen Monitor gegen die Wand schmeißen wenn ich die jedes Mal wieder neu implementieren müsste oder auf die Krücke void* zurückfallen würde.
Wenn man keine Container braucht, sondern eingebettete Strukturen benutzen kann (und ich würde behaupten, das ist fast immer der Fall), dann kommt man in C mit ein bisschen Präprozessoreinsatz recht weit.

Trotzdem sind Templates natürlich schon das C++-Feature, das man in C am ehesten vermisst.
Titel: Re: C oder C++
Beitrag von: bluecode am 20. March 2012, 19:04
Wie gesagt: Datenstrukturen. Zumindest ich würde meinen Monitor gegen die Wand schmeißen wenn ich die jedes Mal wieder neu implementieren müsste oder auf die Krücke void* zurückfallen würde.
Wenn man keine Container braucht, sondern eingebettete Strukturen benutzen kann (und ich würde behaupten, das ist fast immer der Fall), dann kommt man in C mit ein bisschen Präprozessoreinsatz recht weit.
Dann würde ich sowas wie boost's intrusive container(s) (http://www.boost.org/doc/libs/1_35_0/doc/html/intrusive/intrusive_vs_nontrusive.html) bauen.
Titel: Re: C oder C++
Beitrag von: kevin am 20. March 2012, 19:34
Ungefähr sowas baut man dann letztendlich, ja.