Modulares Programmieren vs. OOP



  • operator void schrieb:

    Das heißt natürlich, dass Player von den anderen Objekten wissen muss. Solche "muss wissen von"s, die meistens mindestens eine Extra-Referenz bedeuten, sind meistens das, was mich zu structs treibt, die von eigentlich unbeteiligtem Code verarbeitet werden. Bei so wichtigen Objekten wie dem Spieler würde ich das aber nicht als Argument zählen lassen :p

    Generell muss Player aber nur von einer Basisklasse wissen. Danach kann es heute eine Wand sein gegen die ein Spieler läuft, aber morgen schon ein ganzes Haus. Du könntest z.B. der Wand gegen die der Spieler rennt den Spieler Übergeben und dafür sorgen das die Wand eine Methode kollision aufruft und sich selbst als Basisobjekt übergibt. Das machste bei Haus genauso, bei Hochhaus auch und bei Bretterbude ebenfalls. Ohne für die nachträglchen Häulse Spieler aber auch nur anfassen zu müssen.

    Die Erfahrung die ich beim "Kampf" OOP VS Modulare Programmierung in der Firma gemacht habe ist, das sich keiner gedanken um das Projekt vor der Programmierung machen wollte. Lieber gleich loslegen, ohne Planung. Und dafür ist OOP nun mal nicht geeignet.



  • Was soll an spieler.move_forward() so toll sein? In einer prozeduralen Welt wie C könnte man das gleiche durch player_move(&spieler) erledigen. Dass die Entscheidungslogik nicht an irgendeine beliebige Stelle gehört, sondern in eine eigene Funktion gehört, darauf sind schon andere vor der OOP gekommen.

    An sich würde mich aber schon interessieren, ob irgendeiner von denen, die hier auf SpaceMonkey einschlagen, schonmal ein nicht-triviales Spiel programmiert hat, dass unter den Design-Maßstäben, die er hier im Thread anlegt, bestehen könnte. Ich würd dann gern den Source (oder UML oder was) dazu sehen, lerne nämlich gern dazu 🙂



  • Bashar schrieb:

    Was soll an spieler.move_forward() so toll sein? In einer prozeduralen Welt wie C könnte man das gleiche durch player_move(&spieler) erledigen.

    Natürlich ist das egal. Mir ging es dabei eher darum die Kapselung zu erläutern.

    Denn wir sind uns ja wohl einig dass eine Move-Funktion wichtig ist - um Objekte zu bewegen und dass man nicht direkt die x und y Werte des Objektes ändern sollte, oder?

    Genau das wollte ich zeigen - schließlich geht es hier nicht um OOP vs Prozedualer Programmierung, sondern so wie ich SpaceMonkey verstanden habe - hat er keine struktur in seinem code.

    Ich hoffe auch, dasss wir uns einig sind, dass es egal ist ob man OO, Prozedual, Funktional oder sonstwas programmiert - da generell alle Methoden Sinn machen (Ausnahme: spezielle Probleme, fordern spezielle Lösungen)



  • programmteile die öfter vorkommen in funktionen zu packen mag sicher sinnvoll sein aber das ist ja hier nie zum thema gestanden oder? die x und y werte nie direkt ändern ist ja das konzept der oop 😉 manchmal kann es eben aber auch ganz nett sein wenn man x und y werte der klasse/struct direkt ändern kann besonders eben bei solchen problemen wie kollision oder wenn mehrere spieler gegeneinander laufen. klar mit oop könnte man das sicher auch lösen aber ich will das problem eben direkt angehen und keine klassen erzeugen. für manche hier mag das mit den klassen sicher einfacher und übersichtlicher sein ich will aber direkt mit den werten spielen und wenn teile öfter vorkommen pack ich den code dann in funktionen. zum beispiel initspieler um startwerte zu setzen oder eben zum beispiel die movefunktion. aber eben das ergebnis oop und prozedural ist das gleiche.
    struktur in seinen code zu bekommen kann man auch später erledigen jeder hat eben eine andere arbeitstechnik aber ich bastle eben einfach herum schreibe in meiner hauptschleife füge oben wenn nötig funktionen hinzu 😉 und später kann ich das ganze dann in dateien packen. andere schauen hier gleich auf struktur ich eben nicht. jeder wie er will 😃



  • ich glaube es lohnt sich nicht mit SpaceMonkey weiter zu diskutieren. 🤡



  • ist richtig 🤡 🤡 🤡



  • SpaceMonkey, mit Deiner Argumentation kommst Du mir vor, wie ein Affe der durch's All fliegt... ➡ 😕
    Muahahaha, spitzen Gag, oder?!? ... 🙄



  • Bashar schrieb:

    Was soll an spieler.move_forward() so toll sein? In einer prozeduralen Welt wie C könnte man das gleiche durch player_move(&spieler) erledigen. Dass die Entscheidungslogik nicht an irgendeine beliebige Stelle gehört, sondern in eine eigene Funktion gehört, darauf sind schon andere vor der OOP gekommen.

    Ich habe SpaceMonkeys Anfangspostings nicht so verstanden, dass er nur Probleme mit der OO hat, sondern mit Kapselung allgemein - immerhin will er ja direkt mit den Werten spielen. Da er das innerhalb der Klasse ja problemlos kann, will er es scheinbar auch von außerhalb -> hat auf mich nicht gerade zentralisiert gewirkt.

    Ich code auch oft genug mit structs drauflos, die sich dann allmählich in Objekte verwandeln - oder auch nicht. Mischlinge erlaubt C++ ja problemlos, aber gerade deshalb verstehe ich nicht, warum man nicht zumindest Teil-OO benutzen kann. Warum initspieler wenn ein Konstruktor genausoviel Schreibarbeit wäre?

    Und naja, unfertige Spiele zählen nicht, oder? 🙂 Mittlerweile habe ich es aufgegeben, nur mit der OO zu arbeiten, ohne Vererbungstemplates komme ich nicht weit...



  • ja innerhalb der klasse kann ich sicher mit meinen werten spielen wie ich will. wenn aber eben von außerhalb auch werte gebraucht werden wie jetzt bei der methode moveforward dann tut man sich halt etwas schwerer mit oo. klar ist es auch machbar aber mit structs stellt sich dieses problem erst gar nicht.

    [quote]
    Ich code auch oft genug mit structs drauflos, die sich dann allmählich in Objekte verwandeln - oder auch nicht. Mischlinge erlaubt C++ ja problemlos, aber gerade deshalb verstehe ich nicht, warum man nicht zumindest Teil-OO benutzen kann. Warum initspieler wenn ein Konstruktor genausoviel Schreibarbeit wäre?
    [cpp]

    dem kann ich voll zustimmen. ich programmier einfach auch drauf los später kann man das ganze ja dann in klassen und dateinen packen. ob ich jetzt ne funktoin initspieler oder nen konstruktor verwendet ist egal oder? wegen dem konstruktor ist oo nicht besser und nicht schlechter



  • SpaceMonkey schrieb:

    wenn aber eben von außerhalb auch werte gebraucht werden wie jetzt bei der methode moveforward dann tut man sich halt etwas schwerer mit oo.

    Man muss sich IMHO nicht mehr Gedanken machen als ohne... Ein System ausdenken, über das alle Objekte miteinander kommunizieren, muss man sich so oder so.

    ob ich jetzt ne funktoin initspieler oder nen konstruktor verwendet ist egal oder? wegen dem konstruktor ist oo nicht besser und nicht schlechter

    Der Konstruktor ist für andere (wesentlich) intuitiver und du selbst brauchst du dir keine Gedanken darüber zu machen, initspieler aufzurufen und hast die Garantie, dass der Zustand von Player immer Sinn macht.



  • Man muss sich IMHO nicht mehr Gedanken machen als ohne... Ein System ausdenken, über das alle Objekte miteinander kommunizieren, muss man sich so oder so.

    naja bei prozedural muss ich mir nicht überlegen wie die objekte miteinander kommunizieren ich vergleiche einfach die elemente miteinander 😉

    struct object{
       int x1,x2,y1,y2;
    }object1;
    
    struct player{int x, y,richtung;}player;
    void MovePlayer(player* p){
       if(p->richtung==LINKS){p->x--;}
       else if(p->richtung==OBEN){p->y--;}
       ...
    
       if(p->x>object.x1&&p->x<object.x2&&p->y>object.y1&&p->y<object.y2){
           //player zurücksetzen da er in object ist
       }
       /*hier folgen dann weitere objekte wenn ein neues objekt dazukommt füge
        ich es hier einfach ein muss mir also nicht überlegen wie die 
        objekte miteinander kommunizieren :)*/
    }
    ...
        MovePlayer(&player);
    ...
    

    die vorteile die du über den konstruktor gesagt hast sind zwar ganz nett aber nicht zwindend nötig



  • wenn du wissen willst was deine programme machen musst du auch wissen was in den methoden passiert.

    Nein. Es sei denn du bist ein Idiot. Jeder normale Mensch wählt die Methodennamen entsprechend dessen, was sie tun. Wie sie es tun interessiert mich einen Schießdreck. Ich gehe einfach davon aus, das sie es so effizient wie möglich und völlig korrekt machen, muss micht also nicht mit Kleinkram rumschlagen, sondern kann mich aufs Wesentliche konzentrieren.

    muss nicht auf so belangloses wie ich darf auf dieses element nicht zugreifen weil es privat ist eingehen.

    Wenn dein Design für'n Arsch ist kann ich auch nichts dafür. Wozu brauchst du jemals zugriff auf Implementationsdetails eines Objekts. Ich habe es erlichgesagt noch nie gebraucht.

    vererbung ist fein und gut ist aber auch anderst leicht lösbar eben mit copypaste und ich sehe darin kein problem.

    Nein kannst du nicht. Es geht eigentlich nur um die Polymorphie. Und genau das krigst du nicht durch copy&paste, sondern nur durch sehr hässliche und umständliche Konstrukte. Du müstest dich also mit unnötigem Kleinkram auseinandersetzen, um im Endeffekt auch nur annährend so effizient Programmieren zu können

    ich will jetzt ganz sicher nicht die objektorientierte programmierung schlecht machen. hat sicher auch enorm viele vorteile besonders bei teamprogrammierung und wenn der aspekt wartbarkeit eine wichtige rolle spielt. aber oop muss nicht immer die erste wahl sein. wenn im moment der wartbarkeit oder der übersichtlichlichkeit keine bedeutung geschenkt wird und man allein an einem projekt arbeitet warum sollte man dann oo programmieren? würde ja nur zeit verschwenden...

    Ich programmiere viel alleine und habe trotzdem gigantische Vorteile. Wartbarkeit ist bei mir auf jeden Fall ein Thema, da ich kein Gott bin und gelegentlich Fehler mache, also auch debuggen muss.

    angenommen dein spieler müsste vorwärts laufen aber es könnten vor ihm jede menge objekte liegen die ihn behindern. wie prüfst du jetzt in deiner funktion nach ob vor ihm ein objekt liegt?

    Scheiß drauf. Das wird die Figur schon richtig machen. Wie gesagt, kümmer dich nicht um so einen belanglosen Kleinkram.

    An sich würde mich aber schon interessieren, ob irgendeiner von denen, die hier auf SpaceMonkey einschlagen, schonmal ein nicht-triviales Spiel programmiert hat, dass unter den Design-Maßstäben, die er hier im Thread anlegt, bestehen könnte. Ich würd dann gern den Source (oder UML oder was) dazu sehen, lerne nämlich gern dazu

    Moment. Du willst die Komplette Struktur eines Spiels als UML? Soll ich dir JPEGs schicken? Wie groß ist dein Postfach?
    Aber nicht, das das jetzt Falsch rüberkommt. Bei mir gibts auch einige PODs. Triviale Dinge, wie Punkte stelle ich beispielsweise durch einen POD dar (PODs haben bei mir trotzdem meistens Konstruktore, weil das die Arbeit extrem erleichter.)
    Eine Spielfigur ist aber nichts, was ich als POD darstellen würde, vor allem, weil es viele verschiedene Spielfiguren gibt. Gerade das ist ein tolles Anwendungsgebiet für Polymorphie.
    Aber ich arbeite eigentlch mehr im Audiobereich. Da gibt es dennoch tonnenweise Objekte. Filter, Envelopefollower, ... .



  • 🙂



  • Helium schrieb:

    Moment. Du willst die Komplette Struktur eines Spiels als UML? Soll ich dir JPEGs schicken? Wie groß ist dein Postfach?

    Du kannst es meinetwegen ausdrucken und per LKW vorbeibringen 😉 Ansonsten: JPEG ist nicht für Zeichnungen gedacht, lieber PNG/GIF oder noch besser PS/PDF. Und UML war auch nur ein Beispiel, der Sourcecode geht auch.



  • Wer wie ich, einen Vokabeltrainer (über 14000 Byte) in Basic programmiert zu haben, ohne ein Subroutine zu definieren (alles über Gotos geregelt), kennt die Vorteile von prozeduraler Programmierung gegenüber Spagetti-Code.

    Wer wie ich, einen Funktionsplotter mit Eingabemasken und komplett grafisch in Pascal programmiert hat, ausschließlich mit Funktionen und Structs gearbeitet hat, kennt die Vorteile objektorientierter Programmierung gegenüber prozeduraler/funktionaler Programmierung.

    Immerhin habe ich zum prozeduralen bzw. objektorientierten quasi von selbst gefunden. Mit den Gotos habe ich den Vokabeltrainer quasi in Prozeduren unterteilt, ohne sie so zu nennen/deklrarieren bzw. habe ich für beim Funktionsplotter Funktionen geschrieben, die ausschließlich ganze bestimmte Typen von Structs durcharbeiten konnten (vergl. mit öffentlichen Variablen (privat ging mit Structs nicht) einer Klasse und öffentlichen Methoden einer Klase).



  • Du kannst es meinetwegen ausdrucken und per LKW vorbeibringen

    Du bezahlst?

    Ansonsten: JPEG ist nicht für Zeichnungen gedacht, lieber PNG/GIF oder noch besser PS/PDF. Und UML war auch nur ein Beispiel, der Sourcecode geht auch.

    Mein Fehler. Klar krigst du PNGs.

    Wer wie ich, einen Funktionsplotter mit Eingabemasken und komplett grafisch in Pascal programmiert hat, ausschließlich mit Funktionen und Structs gearbeitet hat, kennt die Vorteile objektorientierter Programmierung gegenüber prozeduraler/funktionaler Programmierung.

    Funktional != Prozedural !!!

    Nur, um mal einen funktionalen Quicksortalgorithmus zu zeigen (Haskell)

    qsort :: Ord a => [a] -> [a]
    qsort []     = []
    qsort (x:xs) = qsort [ y | y <- xs, y < x ] ++ [x] ++ qsort [ y | y <- xs, y >= x ]
    

    (Bitte melden, falls ein Fehler drin sein sollte.)


Anmelden zum Antworten