Guten Abend liebe Programmierer Ich habe eine Frage bezüglich einer sauberen Programmierstruktur. Mittlerweile ist mein Programm relativ gross und ich bemühe mich um einen sturkturierten und sauberen Aufbau. Wie ist eure Meinung zu globalen Variabeln in einem C Programm? Versucht ihr sie eher zu vermeiden, indem ihr mit mehreren return-Anweisungen arbeitet oder sind eure Programme voll mit globalen Variablen? Gruss
Gast
#3271655
Globale Variablen auf das absolut notwendige Minimum beschränken!
Kommt drauf an. Auf einem PC, auf dem du genügend Speicher hast, so dass du kein Auge auf dem zur verfügung stehenden Speicher werfen musst, sind globale Variablen genau das, was du nicht willst. Auf einem kleinen µC, wie den AVR sieht die Sache anders aus. Hier ist die SRAM Größe stark beschränkt, so dass es lebenswichtig ist * den Stack durch nicht zuviele Funktionsargumente zu belasten * den Überblick über den momentanen SRAM Verbrauch zu behalten beides erfordert gloable Variablen, weil nur so die SRAM Statistik ausreichend aussagekräftig ist. Gegen kurze Funktionen mit wenig eigenem Stack-Verbrauch ist trotzdem nichts einzuwenden, aber zumindest die Stammdaten macht man dann als globale Variablen und nicht als Variablen in main(), die man an Funktionen weitergibt. > indem ihr mit mehreren return-Anweisungen return hat allerdings damit nur in Ausnahmefällen zu tun. Wenn eine Funktion einen Wert errechnet, dann spricht nichts dagegen, den aus der FUnktion heruas zu returnieren. An dieser Stelle statt dessen globale Variablen einzusetzen wäre 'strange'. (Arrays sind wie immer die große Ausnahme. Aber ausser Stringverarbeitung hat man das selten auf einem µC)
Chris S. schrieb: > Guten Abend liebe Programmierer > > Ich habe eine Frage bezüglich einer sauberen Programmierstruktur. > Mittlerweile ist mein Programm relativ gross und ich bemühe mich um > einen sturkturierten und sauberen Aufbau. Das ist auf jeden Fall schon mal gut! > Wie ist eure Meinung zu globalen Variabeln in einem C Programm? Versucht > ihr sie eher zu vermeiden, indem ihr mit mehreren return-Anweisungen > arbeitet oder sind eure Programme voll mit globalen Variablen? Globale Variablen sind unter Entwicklern nicht gern gesehen, sind unschön. Das kommt daher, das wirklich globale Variablen (also in Header global.h, welcher überall inkludiert wird) von überall verändert werden können, und dann schnell mal der Überblick verloren geht wer wann zugreift und warum. Wenn ich Mikrocontroller in C Programmiere, habe ich aber auch viele Globale Variablen, ich deklariere die aber immer in einem C File (nie in einem Header file), so, dass diese nur innerhalb des einen Files sichtbar sind. ("privat") Somit habe ich in einem File zusammenhängende Funktionen, und verliere nicht den Überblick über die Zugriffe. Meine persönliche Meinung bei der Mikrocontroller Entwicklung. Bei der Entwicklung von PC Applikationen, egal in welcher Sprache, vermeide ich globale Variablen wenn möglich. (Da entwickle ich aber auch Objektorientiert...) mfg Andreas
Gast
#3271709
> indem ihr mit mehreren return-Anweisungen arbeitet > oder sind eure Programme voll mit globalen Variablen Was hat das eine mit dem anderen zu tun ? Glaubst du
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
funktioniert und wäre vergleichbar mit
1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
Kann ja nicht sein. Funktioniert auch nicht, return 5+i wird nie ausgeführt. Ein C++ Programmierer legt für ein Programm eine Klasse an, von der es eine Instanz im Prozess gibt, und bringt in der Klasse Membervariablen unter, die von Methoden als Seiteneffekt modifiziert werden (das ist auch einfach und eenig Tipparbeit, weil man nur den Variablennamen nenne muss) wodurch sich der Zustand des Objektes ändert. Globale Variablen in normalen C sind Membervariablen vom Prozess. Wenn Funktionen diese als Seiteneffekt ändern, ändern sie den Prozesszustand. Das ist funktionell nichts anderes, nur effizienter. Dennoch sind globale Variablen verschrieen, von den Leuten, die nichts verstanden haben. Man sollte den Rückgabewert einer Funktion mit return liefern, hat sie mehrere Rückgabewerte sollten Parameter auf Variablen zeigen in denen die Werte abgelegt werden sollen, und hat man viele Rückgabewerte sollte eine Struktur ausgefüllt werden. Geht es jedoch nicht um Rückgabewerte, sondern um Änderung des Zustandes des Programms, sind globale Variablen vollkommen in Ordnung. Man muß sich nur klar werden, daß man nur einen Zustand hat. Ein Umkpoieren von Werten aus globalen Variablen nach einem Funktionsaufruf in andere Variablen ist fast immer ein Zeichen, daß man den Unterschied in der empfohlenen Anwendung zwischen globaler Variable und return nicht verstanden hat.
MaWin schrieb: > Dennoch sind globale Variablen verschrieen, > von den Leuten, die nichts verstanden haben. Nicht von Leuten die nichts verstanden haben. Sondern von Leuten die Software ein paar Nummern größer schreiben als du das gewohnt bist. MaWin ich habs dir schon einmal gesagt. Du bist ein Spitzenmann wenn es um Hardware geht. Aber von Software hast du nur einen ganz kleinen SChimmer. Nimm dich nicht als Massstab dafür, was vernünftiges Softwaredesign ist. Mit Leuten, die Ansichten wie du haben,, hab ich jeden Tag zu tun. Und ich (und nicht nur ich) würde sie am liebsten jeden Tag 2 mal auf den Mond schiessen.
Wenn der Aufrufer mit dem Ergebnis weiter arbeiten soll, ist ein Returnwert vorzuziehen. Sind mehrere Werte zurück zu geben, kann man eine Struct als Returntyp definieren. Das ergibt nebenbei auch schnelleren, kürzeren Code und weniger RAM-Verbauch, da der Wert in Registern übergeben werden kann.
Gast
#3271990
Chris S. schrieb: > Wie ist eure Meinung zu globalen Variabeln in einem C Programm? Ich schätze, du verwechselst da was. Wahrscheinlich meinst du den Unterschied zwischen Variablen, die statisch im RAM angeordnet werden (das sind alle, die du außerhalb von Funktionen/Prozeduren anlegst) und solchen, die nur innerhalb eines Unterprogramms deklariert und benutzt werden und die deshalb auf dem Stack angelegt werden. Mach dir einfach die simple Regel zueigen, daß man nur das als Argument einer Funktion übergibt, was bei verschiedenen Aufrufen dieser Funktion auch tatsächlich unterschiedlich sein kann. Argumente, die immer wieder die gleichen sind, sind albern und machen nicht nur mehr Streß, sondern blähen auch den Code auf. Ansonsten entscheide einfach selber nach deinem (hoffentlich qualifizierten) Gutdünken, welche Variablen du dem Stack zumuten willst und welche du lieber statisch im RAM haben willst. Alle solche Sprüche wie "Globale Variablen auf das absolut notwendige Minimum beschränken!" kannst du getrost in den Skat drücken. Wer so generalisiert, hat mit Sicherheit keinen wirklichen Überblick und wiederholt nur Sprüche seines Lehrers von anno Toback. Gleiches gilt übrigens auch für "goto ist Spaghetticode und ist deshalb strikt zu vermeiden!" Wie sind doch ganze Generationen von C-Hasenschülern auf solche Sprüche dressiert worden, bloß weil 'goto' im Basic der 80er Jahre ne Notwendigkeit war und alle Homecomputer-Kinder, die mal Programmierer werden wollten, eben Basic verinnerlicht hatten und mit Prügeln zu C hin umdressiert werden mußten. W.S.
Gast
#3272003
> > Dennoch sind globale Variablen verschrieen, > > von den Leuten, die nichts verstanden haben. > Nicht von Leuten die nichts verstanden haben. Doch, genau von denen, wie du es gerade bestätigt hast. > Aber von Software hast du nur einen ganz kleinen SChimmer. Du hast schon Betriebssysteme geschrieben ? Du hast schon Compiler geschrieben ? Du hast schon Textverarbeitungsprogramme geschrieben ? Du hast schon Chart-Graphik-Programme geschrieben. Du hast schon Spiele geschrieben. Du hast schon Windows Applikationen geschrieben. Du hast schon Smartphone-Applikationen geschrieben. Du hast schon Flugnavigationssoftware geschrieben. Du hast schon GUIs geschrieben (also Window Manager und GDI) Du hast schon Mathematik-Libraries geschrieben (Cordic & co.) Du hast schon Statistik-Libraries geschrieben. Du hast schon Druck-Postprozessing geschrieben. Du hast schon Gerätetreiber geschrieben. Du hast schon Interpreter und Debugger geschrieben. Warum nur glaube ich das nicht. Ganz einfach, weil deine Aussagen so typisch sind für jemanden, der das alles noch nie getan hat.
Gast
#3272011
MaWin schrieb: >> > Dennoch sind globale Variablen verschrieen, >> > von den Leuten, die nichts verstanden haben. >> Nicht von Leuten die nichts verstanden haben. > > Doch, genau von denen, wie du es gerade bestätigt hast. > >> Aber von Software hast du nur einen ganz kleinen SChimmer. Jeder der schon mal versucht hat ein Programm zur Optimierung Multithreadet zu machen, stolpert früher oder später über globale Variablen. Denn auf einmal hat das Programm nicht mehr nur einen Status sondern mehre gleichzeitig. Wenn sie const sind, kann man sie verwenden, aber im Normalfall sind sie zu vermeiden auch wenn du davon nicht überzeugt bist.
Gast
#3272023
> Jeder der schon mal versucht hat ein Programm zur Optimierung > Multithreadet zu machen, stolpert früher oder später über globale > Variablen. Dann schubst man die globalen Variablen als Members in eine Prozess-Klasse, alle Funktionen die auf diesen Variablen arbeiten als Methoden auch dahinein, und hat mit self einen Bezug auf den aktuellen Thread. Das ist kein Problem, und kein Grund, ein Programm, welches NICHT multithreaded ist und es mit 99.99%iger Sicherheit niemals werden wird, mit dem Ballast eben dieser Klasse (indirekter Zugriff auf Member und zusätzlicher Parameter bei Mathoden) zu belasten. Diesen Zusammenhang (global = members des Prozesses) hatte ich oben schon beschrieben, du hast es offenbar übersehen.
Gast
#3272029
Peter II schrieb: > MaWin schrieb: >>> > Dennoch sind globale Variablen verschrieen, >>> > von den Leuten, die nichts verstanden haben. >>> Nicht von Leuten die nichts verstanden haben. >> >> Doch, genau von denen, wie du es gerade bestätigt hast. >> >>> Aber von Software hast du nur einen ganz kleinen SChimmer. > > Jeder der schon mal versucht hat ein Programm zur Optimierung > Multithreadet zu machen, stolpert früher oder später über globale > Variablen. Denn auf einmal hat das Programm nicht mehr nur einen Status > sondern mehre gleichzeitig. Nicht unbedingt. Oder man muss das Programm genauer eingrenzen. Jeder von uns, der (Mikro)Prozessoren programmiert, arbeitet permanent mit globalen Variablen und findet das auch völlig legitim - egal ob multithreaded oder gar auf mehreren Kernen. Als solche globalen Variablen treten beispielsweise die SFRs des Prozessors in den C-Sprachraum. Die beschreiben im einfachsten Sinne nämlich genau den von MaWin erwähnten Zustand des 'Programms'. Und schließlich wird eine Variable nicht weniger global, nur weil man sie hinter Singletons o.ä. versteckt. Das mag den Zugriffsmechanismus regeln (zum Beispiel mit einer Verriegelung bei multithreaded), aber global ist die Variable zumindest semantisch immer noch. Und das ist ja auch in Ordnung so.
Gast
#3272041
MaWin schrieb: > Das ist kein Problem, und kein Grund, ein Programm, welches > NICHT multithreaded ist und es mit 99.99%iger Sicherheit > niemals werden wird, mit dem Ballast eben dieser Klasse > (indirekter Zugriff auf Member und zusätzlicher Parameter > bei Mathoden) zu belasten. Du solltest als Hellseher auftreten, ich kann von meinen Programm nie mit 99% Sicherheit sagen wie sie sich in Zukunft entwickeln werden. Übrigens gibt es ausreichend libs wie z.b. libpng die das scheinbar auch gedacht haben. Sobald man sie in einen Multitheaded Programm verwendet knallt ist. (keine Ahnung ob die aktuell Version noch betroffen ist) Lieber gleich richtig machen, als später umbauen.
Gast
#3272042
MaWin schrieb: > Du hast schon Compiler geschrieben ? > Du hast schon Textverarbeitungsprogramme geschrieben ? > Du hast schon Chart-Graphik-Programme geschrieben. > Du hast schon Spiele geschrieben. > Du hast schon Windows Applikationen geschrieben. > Du hast schon Smartphone-Applikationen geschrieben. > Du hast schon GUIs geschrieben (also Window Manager und GDI) > Du hast schon Mathematik-Libraries geschrieben (Cordic & co.) > Du hast schon Gerätetreiber geschrieben. > Du hast schon Interpreter und Debugger geschrieben. Jep. Fuer die paar, die ich streichen musste, habe ich Ersatz, zum Beispiel Filesysteme, diverse Plugins, etc. Wie viele Treffer auf deiner Liste kannst du verzeichnen? Zur Sache hat Karl Heinz mal wieder Recht - du nicht.
Gast
#3272044
MaWin schrieb: > Du hast schon Betriebssysteme geschrieben ? [...] All das kann man so oder so machen, mit mehr oder weniger Erfolg... Nur weil man etwas irgendwie mal programmiert hat muss das nicht notwendigerweise gut gewesen sein. Besonders in Industrie-und Nischenanwendungen trifft man auf viel hoch gelobte & als der Weisheit letzter Schluss deklarierte Software die dann doch ziemliche Sch**e ist.
Gast
#3272612
> Du solltest als Hellseher auftreten, ich kann von meinen Programm nie > mit 99% Sicherheit sagen wie sie sich in Zukunft entwickeln werden. Aber du baust schon alles ein damit es alle möglichen vielleicht mal nötigen Änderungen "vorbereitet" hat. Du bist der Hellseher. Die am schlechtesten wartbaren Programme sind übrigens solche Käse-Schinken, die haufenweise derzeit nutzlosen code enthalten. Ausserdem ist dein Programm damit teurer als nötig (oder schlechter zum selben Preis) weil du dich mit Arbeiten beschäftigst, die der Kunde gar nicht bestellt hat. > Wie viele Treffer auf deiner Liste kannst du verzeichnen? Alle. Und natürlich enthält ein Betriebssystem ein Filesystem und natürlich schreibt man Plugins, beispielsweise Importfilter. > Nur weil man etwas irgendwie mal programmiert hat muss das nicht > notwendigerweise gut gewesen sein. Egal wie man es gemacht hat, man hat daraus gelernt, und wie ich an euren Beiträgen sehe, habt ihr noch nichts gelernt. Bei den allermeisten vermisse ich sogar den selbstverständlichen Grundlagenstand eines entsprechenden Studiums.
MaWin schrieb: > habt ihr noch nichts gelernt. Doch, allerdings unterscheidet sich der erzielte Lerneffekt der meisten von uns offenbar diametral von deinem. Das ist dann ein bisschen wie mit dem Falschfahrer auf der Autobahn … „Was, einer? Alle!“
Gast
#3272741
> Das ist dann ein bisschen wie mit dem Falschfahrer auf der Autobahn > … „Was, einer? Alle!“ Ganz einfach Jörg: Guck auf die Schilder, in diesem Fall das was dir in der Informatik-Vorlesung erzählt wurde (falls du so was überhaupt mal mitbekommen hast, klingt eher nicht danach). Du (weiss ich gar nicht, hab's bisher nur von anderen gelesen) wollen sich einfach ihre lasche Arbeitsweise und miesen Ergebnisse schönreden und als angeblichen Stand der Technik (damit haben sie teilweise Recht, fehlerhafte fette Programme sind leider üblich) als ausreichend hinlügen. Klar, meine Programme sind auch nicht optimal, aber wenigstens weiß ich das und rede es nicht schön, und vor allem: Ich schreibe nicht absichtlich unoptimalen Code und erfinde für die falsche Richtung jede Menge Ausreden.
Sehr unterhaltsamer Thread :-)
MaWin schrieb: > Du (weiss ich gar nicht, hab's bisher nur von anderen gelesen) wollen > sich einfach ihre lasche Arbeitsweise und miesen Ergebnisse schönreden Komisch. Genau diesen Eindruck haben wir alle von dir …
Gast
#3273472
Jörg Wunsch schrieb: > Komisch. Genau diesen Eindruck haben wir alle von dir Du machst dich lächerlich, und du weisst es bereits selber, holst du doch "wir alle" die imaginäre Masse zum vermeintlichen Schutz hinter dich. Auch bist du wirklich auf Kindergartenniveau, einfallslos einfach "dasselbe" vom Gegenüber zu behaupten.
@MaWin Hast du eigentlich Freunde? mfg.
Gast
#3273717
Ich kann nicht klagen, heute haben mich 3 von denen besucht.
Gast
#3273755
Ich wäre dann ein Teil von Jörgs imaginärer Masse. Und dass man ein Betriebssystem programmiert hat, sagt noch nicht, dass man in allen Fragen Recht hat (Wie beispielsweiße der gute Andre Tannenbaum feststellen musste: Irgendwie ist dieses total veraltete Linux immernoch nicht tot, obwohl Minix doch so viel besser ist) Und ja, manchmal machen globale Variablen auch am PC sinn. Das sind aber eher ausnahmen, meistens kann man mit einem Bisschen Zusatzaufwand eine mindestens gleichwertige Lösung finden, die, falls das Programm weiterentwickelt werden soll, weniger Probleme bereitet. Auf nem µC empfielt sich in dem Zusammenhang noch das Schlüsselwörtchen static für globale Variablem, damit prüft dann der Compiler gleich mit, dass sie nur in ihrer Übersetzungseinheit verwendet werden. Was MaWins Unoptimiertheit von Code ohne Globale Variablen angeht: 1) Voreilige Optimierungen haben meist gegenteiligen Effekt. Falls es da Verbesserungen zu holen gibt, wird der Compiler einen guten Teil davon schon rausholen. 2) Spätestens, wenn Caches ins Spiel kommen, ist der Vorteil weg, weil die Variablen entweder dauerhaft im Cache gehalten werden müssen (und damit den Cache verschwendet) oder aber doch dann, wenn sie gebraucht wird einfach mitübergeben wird. Und damit wäre es doppelter Aufwand. Gleiches trifft auf GOTO zu: Es hat offensichtlich eine Verwendung, sonst wäre es nicht in C und dann auch noch in C++ gelandet. Man kann zum Beispiel Pseudo-Exceptions auf nem µC in C damit realisieren. Oder Informatiklehrer (und sich selbst) in die Verzweiflung treiben. Aber: Auch wenn die Verwendung sinnvoll sein kann - In 99.9% der Fälle ist sie es eben nicht, sondern ein Ausdruck dessen, dass da am Gesammtkonzept was nicht stimmt.
Falls Chris S. noch spezifische Fragen hat möge er bitte einen neue Thread eröffnen, hier kommt denke ich nichts mehr rum was mit dem ursprünglichem Thema zu tun hätte.