cplusplusser schrieb:> Das ist doch etwa so, als würdest du behaupten, die Post brauche keine> LKWs, weil ein Brief ja schliesslich in eine Jackentasche passt.
Nein, du willst unbedingt ein Brief mit LKW zustellen, anstatt einen
Postboten hinzuschicken.
> Oder es> brache keine Flugzeuge, weil zwischen den beiden Flughäfen deiner Stadt> eine U-Bahn fährt.
Nein, du willst unbedingt von einem Flughafen zum anderen fliegen,
anstatt die U-Bahn zu nehmen.
Moby schrieb:> Also Klaus, Du enttäuscht mich besonders ;-(
Ich habe in dem Forum zu C++ schon etwas mehr beigetragen als die
meisten andern, vor allem etwas differenzierter als dein Getrolle.
Liest nur nicht jeder - was mir auch nicht weh tut. Aber dann bitte
nicht blöd herumtrollen. Vor allem scheinst du mein "OOP-Weltbild" nicht
zu kennen.
Moby, kann es sein dass du bei C++ nur an OOP denkst. Dann bist du aber
wirklich naiv. Ob nun OOP für 8Bit µCs sinnvoll ist oder nicht, ist eine
ganz andere Diskussion. OOP ist nur ein Paradigma. C++ beherrscht mehr
als nur eines (genau genommen lässt sich in C++: generisch, imperativ,
objektorientiert, prozedural, strukturiert programmieren).
Templates sind z.B. eine hübsche Möglichkeit Code zu sparen ohne
weiteren Overhead. Man schreibt einmal eine Funktionalität und diese
lässt sich dann auf alle Datentypen anwenden, solang das mit dem
jeweiligen Datentyp Sinn ergibt. Das ist Effizienz! Ein geniales
Konzept, was man schnell vermisst (auch auf 8Bit µCs). Und C++ kann noch
viel mehr.
Moby schrieb:> Rolf Magnus schrieb:>> Es sollte doch klar sein, daß Erkenntnisse, die sich aus Trivialfällen>> ergeben, sich nicht einfach so auf die reale Welt übertragen lassen.>> Interessant daß Du den Trivialfall nicht zur realen Welt zählst ;-)
Kapierst du es nicht? Du reduzierst es auf den Trivialfall und folgerst
dann daraus, es sei allgemeingültig. Ein Kreis mit Radius 0 hat die
Fläche 0, also haben alle Kreise die Fläche 0, also brauche ich diese
blöde Formel mit Pi und so nicht zur Flächenberechnung.
Aber Moby, ganz ehrlich: Setz dich mal 5 Minuten hin und denke darüber
nach, was du hier gerade abziehst. Wenn du dich im realen Leben in einem
Fachgespräch so gibst, dann wundert mich nicht, wenn du danach in
Ausbildung&Beruf einen Thread startest mit dem Titel "Warum nimmt mich
auf Arbeit keiner Ernst?".
Es ist ja schön und gut, wenn man in einer Diskussion seine Position
verteidigt. Und du liegst auch nicht in allen Punkten falsch. Aber wer
so stur auf einzelnen Positionen herumreitet, obwohl ihm schon 5 Leute
gesagt haben, dass dies nun wirklich der falsche Ansatz ist, der sollte
echt mal ein wenig herauszoomen und sich fragen, ob es jetzt noch um die
Sache geht oder nur noch um die Angst vor einem Gesichtsverlust.
cplusplusser schrieb:> Ok. Du nimmst also die vermutlich einfachste Aufgabe, die es gibt. Dann> erklärst du, dass man die mit ein paar Assembler-Anweisungen lösen kann.> Dann folgerst du daraus, dass man auf einem Mikrocontroller keine OOP> braucht.
Na ja, fast den Nagel auf den Kopf getroffen. Obwohl Du wieder mal die
Eingrenzung auf Hardwarenah unterschlagen hast. Und meine Eingrenzung
Moby schrieb:> Jedenfalls was eine typische 8-Bit> Controllerschaltung mit überschaubarer Funktionalität anbetrifft.
Um mit Deinen hübschen Beispielen zu sprechen, ja, ein paar Briefe
können in der Jackentasche durchaus schneller transportiert werden und
der Post-LKW in der Garage bleiben- wie auch die U-Bahn Flugzeuge
obsolet machen kann. Denn der Fall, daß sich quasi alles in einer
überschaubaren Stadt abspielt tritt bei obigem Schaltungstyp in
Millionen Steuerungsanwendungen wesentlich häufiger auf als in Deinem
Vergleich Entfernungen realer Briefe und Orte überbrückt werden müssen
;-)
Manchmal ist es leider aber so, daß Flugzeuge und Postautos (ARM & OOP)
schon draußen stehen und auf Anweisung benutzt werden müssen.
Glücklicherweise ist der freie Bastler aber in der Wahl seiner
(einfachsten) Mittel frei ;-)
>Der Typ erinnert mich irgendwie an einen gewissen Kurt.>Fehlt nurnoch die Floskel: "da schwingt überhaupt nichts..."
Mich erinnert es eher an das hier:
http://www.youtube.com/watch?v=akfz5Fw-pZI
TriHexagon schrieb:> Templates sind z.B. eine hübsche Möglichkeit Code zu sparen ohne> weiteren Overhead. Man schreibt einmal eine Funktionalität und diese> lässt sich dann auf alle Datentypen anwenden, solang das mit dem> jeweiligen Datentyp Sinn ergibt. Das ist Effizienz!
Nun TriHexagon, effizient ist für mich kleinster/schnellster Code mit
minimalem Schreibaufwand der die Funktionalität 1:1 abbildet, ohne jedes
weitere Hochsprachen-Bimbamborium. Ich mach mir weder wegen Datentypen
noch irgend einem anderen C(++) Konstrukt Sorgen, glaub mir.
cplusplusser schrieb:> Angst vor einem Gesichtsverlust
Die plagt mich am allerwenigsten ;-)
cplusplusser schrieb:> obwohl ihm schon 5 Leute> gesagt haben, dass dies nun wirklich der falsche Ansatz ist,
Wie war das doch gleich nochmal mit den Millionen Fliegen die nicht
irren?
Schau cplusplusser, ich wünsch Dir ja viel Freude bei Deiner unbedingten
C++ Anwendung auf alles nur Denkbare. Aber Du siehst ja selbst, viele
Designkonzepte sind hier diesbezüglich nicht zusammengekommen ;-(
Moby schrieb:> Nun TriHexagon, effizient ist für mich kleinster/schnellster Code mit> minimalem Schreibaufwand der die Funktionalität 1:1 abbildet, ohne jedes> weitere Hochsprachen-Bimbamborium. Ich mach mir weder wegen Datentypen> noch irgend einem anderen C(++) Konstrukt Sorgen, glaub mir.
Für den einzigen bekannten Anwendungsfall in Moby's Welt (LED ein/aus)
ist das sicher der richtige Weg. Für alles andere hat man Hochsprachen
und Programmierkonzepte entwickelt.
cplusplusser schrieb:> Für den einzigen bekannten Anwendungsfall in Moby's Welt (LED ein/aus)> ist das sicher der richtige Weg.
... und noch für soviel mehr!
Immerhin schränkst Du Deinen C++ Anspruch nun schon etwas ein, bravo.
Aus einer LED werden zwei ... ;-)
bal schrieb:> Fehlt nurnoch die Floskel: "da schwingt überhaupt nichts..."
Darauf kannst Du lange warten...
Meine vielen AVRs vibrieren nur so vor Arbeitsfreude.
Und manche sogar schon viele Jahre lang ;-)
Klaus Wachtler schrieb:> Ja gut, einen Dildo kann man leicht in ASM programmieren :-)
Dieses Niveau hatte ich jetzt bei Dir nicht angenommen.
Du enttäuscht mich schon wieder, Klaus ;-)
falls es wen interessiert, hier ein link zu recht extremem C++ Code, der
auch auf atmegas läuft... viel spass beim lesen ;-)
https://github.com/ambrop72/aprinter
Klar geht das - der Header wird doch eh nur textuell
kopiert/eingefügt.Ob das Sinn macht, steht auf einem anderen Blatt und
kommt immer drauf an...
"With great power comes great responsibility" ;)
Franz schrieb:> Wie schon erwähnt, Hessi James passt ganz gut auf Mobby.
Lustig. Immerhin bringt der Titelheld Leben in die vertrocknete
Landschaft. Was der Situation nicht gewachsen ist geht eben unter ;-)
cplusplusser schrieb:> mittlerweile ist das doch nur noch trollig.
Man muß doch nicht alles als "trollig" abqualifizieren nur weils nicht
ins persönliche Weltbild paßt. Ich wäre mit solcherlei Abwertungen eher
vorsichtig, es sei denn die Absicht ist so eindeutig wie bei den letzten
Aussagen eines gewissen Klaus.
Franz schrieb:> Entschuldigt, wenn ich jetzt doch eine On-Toppic Frage stelle.> Bei dem geposteten Link> https://github.com/ambrop72/aprinter/tree/master/aprinter/base> wird der Code z.Teil in die Header-Files gesteckt. Geht das? Macht das> Sinn?
Das sind Makros und Templates. Die können nicht einzeln kompiliert und
gelinkt werden. Denn die Makros werden vom Präprossor verarbeitet und
bei den Templates muss der Compiler die Implementierung kennen (so kann
er dazu auch noch einiges weg optimieren).
Womit wir übrigens wieder BTT wären: Wenn der Compiler z.B. entscheidet,
welche Sachen er inlined und welche nicht, dann habe ich abhängig von
den Randbedingungen wie zB. 'wenig RAM und einigermaßen viel Flash' doch
eventuell ein Problem, das in diesem Fall von einem C++-Konzept
induziert wird, oder sehe ich das falsch?
In aller Regel kann man die Grenze, bis zu der tatsächlich inline-Code
erzeugt wird, per Compileroption verschieben.
Damit kann man von Fall zu Fall Flash gegen Laufzeit tauschen in
gewissen Grenzen.
Tobias K. schrieb:> Womit wir übrigens wieder BTT wären: Wenn der Compiler z.B. entscheidet,> welche Sachen er inlined und welche nicht, dann habe ich abhängig von> den Randbedingungen wie zB. 'wenig RAM und einigermaßen viel Flash' doch> eventuell ein Problem, das in diesem Fall von einem C++-Konzept> induziert wird, oder sehe ich das falsch?
Umgekehrt. Wenn du dein Programm auf einer höheren Abstraktionsebene
definieren kannst, dann gibst du dem Compiler auch viel mehr Raum für
Optimierungen. Wenn die Randbedingung von "genügend Zeit, Speicher
knapp" auf "so schnell wie möglich, reichlich Speicher" wechselt, dann
schreibt Moby seinen Code garantiert komplett neu.
Moby schrieb:> Lustig. Immerhin bringt der Titelheld Leben in die vertrocknete> Landschaft. Was der Situation nicht gewachsen ist geht eben unter ;-)
Untergehen tun vorallem Trolle, wenn sie nicht gefüttert werden. Leider
bist du auf ein äusserst diskutierfreudiges Publikum gestossen mit
deiner Trollerei. (Ich hoffe jedenfalls, du bist ein Troll. Falls nicht:
Wenn ich nur daran denke, dass man im Berufsleben auf jemanden treffen
könnte, der so argumentiert wie du, na dann, gute Nacht...)
cplusplusser schrieb:> Untergehen tun vorallem Trolle, wenn sie
komplexe, fehleranfällige, rechenzeit- und speicherbelegende
Programmiertechniken predigen, die Millionen einfachen 8-Bit Power
Steuerungslösungen nur sinnlos aufblähen und verkomplizieren.
Leider bist Du auf einen Praktiker aus Leidenschaft gestoßen, der sich
damit für vielfältigen eigenen Bedarf schon zulange beschäftigt.
Du kannst Dich aber praktischen Problemstellungen gerne weiter versuchen
philosophisch anzunähern- vielleicht findest Du doch noch einen ganz
neuartigen Zugang zu deren Lösung ;-)
Moby schrieb:> komplexe, fehleranfällige, rechenzeit- und speicherbelegende> Programmiertechniken predigen,
Wogegen deine Technik (wie du sie oben beschrieben hast, "IP-Stack")
ist:
Du programmierst alles in ASM, und wenn es dir zu Kompliziert wird,
nimmst du einen zweiten µC (nicht unbedingt einen AVR) für den jemand
anders in C(++) die Firmware geschrieben hast, und verbindest ihn mit
deinem ASM-AVR...
Moby schrieb:> husten schrieb:>> wer schonmal einen IP stack geschrieben hat>> Ist ja schon fast ein Running Gag kontra Asm.> Mensch, der steckt heute schon in jedem 2€ China ESP8266 Modul drin.> Sowas flanscht man bei Bedarf an und gut ist.
vorgabe war : LAN .. was soll ich also mit einem WLAN chip?
ebenso vorgabe : billig ... da ist kein ct übrig für ein Wiznet oder
anderen fertigen LAN chip ..
hmm was nun ?
AVR+ ENJ28? zusammen leider teurer als ein Cortex M3+phy ...
und ebenso zu langsam ...
denn im PH steht vorgabe : datenrate xxMbit/s
damit bleiben nur die total unnötigen 32bitter übrig ...
also PIC32,Cortex M usw ...
cplusplusser schrieb:> Wenn ich nur daran denke, dass man im Berufsleben auf jemanden treffen> könnte, der so argumentiert wie du, na dann, gute Nacht...)
:-D
Hat er denn ein Berufsleben?
bisher lese ich nur :
Moby schrieb:> Glücklicherweise ist der freie Bastler aber in der Wahl seiner> (einfachsten) Mittel frei ;-)
und hat demnach auch keine erfahrung mit der industrieellen entwicklung
.. evtl wo sogar mehrere leute an einem Projekt sitzen und software
schreiben sollen.
denn spätestens da .. ist C/C++
Moby schrieb:> Manchmal ist es leider aber so, daß Flugzeuge und Postautos (ARM & OOP)> schon draußen stehen und auf Anweisung benutzt werden müssen.
manchmal auf anweisung ..
manchmal weil es die lesbarkeit bei größeren Projekten deutlich
verbessert...
wer schonmal in 1-5jahre alten quellcodes ( mehr als ein sbi )
features nachgestrickt hat kennt das
da möchte ich nicht in tausenden zeilen ASM stellen suchen um etas zu
ändern.
in C / C++ geht soetwas recht einfach ..
Moby schrieb:> Leider bist Du auf einen Praktiker aus Leidenschaft gestoßen, der sich> damit für vielfältigen eigenen Bedarf schon zulange beschäftigt.
Vielfältigen eigenen Bedarf? Bisher hast du nur immer von deiner LED
erzählt. Was du sonst noch so in Assembler geschrieben hast, davon liest
man kein Wort.
(Wobei das Wort Praktiker ja sowieso ein gerne gebrauchter Euphemismus
für Leute ist, die ihre Projekte ohne wirklichen Durchblick
hinfrickeln...)
husten schrieb:> wer schonmal in 1-5jahre alten quellcodes ( mehr als ein sbi )> features nachgestrickt hat kennt das> da möchte ich nicht in tausenden zeilen ASM stellen suchen um etas zu> ändern.> in C / C++ geht soetwas recht einfach ..
Aber auch nur wenn es reichlich kommentiert ist...
husten schrieb:> und hat demnach auch keine erfahrung mit der industrieellen entwicklung> .. evtl wo sogar mehrere leute an einem Projekt sitzen und software> schreiben sollen.> denn spätestens da .. ist C/C++
Auch wieder ausreichend kommentiert. Wir haben in unseren Projekten ein
70 zu 30 Anteil, also 70% Code und mindestens 30% Prozent Kommentare.
Niemanden interessiert es da besonders kurzen Code zu sehen, aber alle
wollen wissen warum etwas gerade so geschrieben ist und was es genau
bewirkt.
cplusplusser schrieb:> Optimierungen. Wenn die Randbedingung von "genügend Zeit, Speicher> knapp" auf "so schnell wie möglich, reichlich Speicher" wechselt, dann> schreibt Moby seinen Code garantiert komplett neu.
Und das hat mit C++ was genau zu tun ? Kann man mit plain C auch.
C++ und Hardware haben genau nichts miteinander zu tun - weder Vor-
noch Nachteile im Vergleich zu plain C.
Um noch einmal deinen Beispiel zu nehmen:
Die Post wird auch keinen LKW nehmen um einen Brief zuzustellen, nur
weil der Postbote älter als LKW ist, keine 8-Gang Schaltung, Navi und
Radio hat.
Auch auf die Gefahr hin, daß die von cplusplusser gesuchten
Designkonzepte hier irgendwann völlig verdeckt werden ;-) ...
Ahab schrieb:> Wogegen m(d)eine Technik (wie du sie oben beschrieben hast, "IP-Stack")> ist
vorhandenes nicht zweimal zu erfinden wenn es günstig genutzt werden
kann (zählt zum Thema Effizienz bei der Problemlösung). Wie das
Innenleben angeflanschter Hardware ausschaut ist dann absolut
zweitrangig. Daß komplexe Programme mit vielerlei Datenstrukturen anders
als mit Asm anzupacken sind bestreitet auch niemand.
husten schrieb:> damit bleiben nur die total unnötigen 32bitter übrig ...
Wo ist das Problem, wenn die Leistung wirklich erforderlich ist?
Die Stückzahlen vermehrte Softwarekosten wieder reinholen?
Das ist weit weg vom Thema, C++ in jeder Situation anwenden zu wollen.
husten schrieb:> und hat demnach auch keine erfahrung mit der industrieellen entwicklung> .. evtl wo sogar mehrere leute an einem Projekt sitzen und software> schreiben sollen.> denn spätestens da .. ist C/C++
Ja! Ja doch! Dann nutzt doch C++ !
Das ist aber wieder weit weg vom Thema, C++ in jeder Situation anwenden
zu wollen.
husten schrieb:> weil es die lesbarkeit bei größeren Projekten
Ja! Ja doch! Größere Projekte!
husten schrieb:> da möchte ich nicht in tausenden zeilen ASM stellen suchen
Ich kann dazu nur feststellen: Asm hat hinsichtlich der
Dokumentierbarkeit keinerlei Nachteile. Es ist auch da die Frage wie man
ein Projekt aufbaut. Prädestiniert ist Asm aber für kleinere Sachen.
Sachen aber, die in die Millionen gehen!
cplusplusser schrieb:> die ihre Projekte ohne wirklichen Durchblick> hinfrickeln
Danke. Und Dir fehlt der Durchblick, was Dir hier einige Gegenspieler
ans Herz gelegt haben. Nimmst vieles nicht zur Kenntnis. Hast gar nicht
verstanden, was Dir das Beispiel mit der Blinkschaltung sagen soll oder
willst es eben nicht. Besser wäre wirklich
W.S. schrieb:> Schlaf mal drüber, ehe du in die Tasten haust.
Tut mir langsam leid, daß ich andauernd kaltes Wasser in Deine heiße C++
Begeisterung gieße.
Marc Vesely schrieb:> husten schrieb:>> wer schonmal in 1-5jahre alten quellcodes ( mehr als ein sbi )>> features nachgestrickt hat kennt das>> da möchte ich nicht in tausenden zeilen ASM stellen suchen um etas zu>> ändern.>> in C / C++ geht soetwas recht einfach ..>> Aber auch nur wenn es reichlich kommentiert ist...>> husten schrieb:>> und hat demnach auch keine erfahrung mit der industrieellen entwicklung>> .. evtl wo sogar mehrere leute an einem Projekt sitzen und software>> schreiben sollen.>> denn spätestens da .. ist C/C++>> Auch wieder ausreichend kommentiert. Wir haben in unseren Projekten ein> 70 zu 30 Anteil, also 70% Code und mindestens 30% Prozent Kommentare.> Niemanden interessiert es da besonders kurzen Code zu sehen, aber alle> wollen wissen warum etwas gerade so geschrieben ist und was es genau> bewirkt.
das ist auch eine starke abhängigkeit vopm "C(C++" stil ...
selbst schon erlebt ...
meine kollegen schreiben alles in zig "states" und unterteilen jedes
noch so kleine fitzel in "states" oder "events"
ich mag funktionszeiger und verschachtele dadurch alles mögliche als
callback funktion...
im groben und ganzen isses aber egal ...
wenn die variablen/funktionen halbwegs brauchbare namen haben.
wenn man mit ebenso cryptischen namen anfängt oder nur mit
i,k,l... x,y,z um sich wirft ... nunja ...
das erschwert die lesbarkeit
ebenso muss man ja nicht alles komprimieren
dafür gibts dann IOCC ^^
http://www0.us.ioccc.org/2013/cable2/cable2.c
Marc Vesely schrieb:> C++ und Hardware haben genau nichts miteinander zu tun - weder Vor-> noch Nachteile im Vergleich zu plain C.
Nach diesem Thread noch sowas zu behaupten, finde ich eine schlichte
Frechheit. Immerhin wurden genügend Beispiele gebracht, wo C++ auch für
Mikrocontroller eine gute Option ist und wo man auch die Hardware-Ebene
noch beherrscht. Mag sein, dass man C++ nicht mag oder für seine
Projekte Overkill findet, ok.
Moby schrieb:> Hast gar nicht> verstanden, was Dir das Beispiel mit der Blinkschaltung sagen soll oder> willst es eben nicht. Besser wäre wirklich
Mit einem Trivialfall kann man die Welt nicht erklären, das merkst du
aber irgendwie nicht. Wenn ich mir zudem ansehe, wer eher meine und wer
eher deine Position teilt, dann ist für mich eigentlich alles klar :-)
cplusplusser schrieb:> Nach diesem Thread noch sowas zu behaupten, finde ich eine schlichte> Frechheit. Immerhin wurden genügend Beispiele gebracht, wo C++ auch für
Bitte um ein einziges Beispiel wo C++ beim Hardwarezugriff Vorteile
gegenuber plain C bringt.
Marc Vesely schrieb:> Bitte um ein einziges Beispiel wo C++ beim Hardwarezugriff Vorteile> gegenuber plain C bringt.
inline
(ist bei gcc z.B. auch mit C möglich, aber eben nicht portabel - in C++
im Standard)
Marc Vesely schrieb:> Bitte um ein einziges Beispiel wo C++ beim Hardwarezugriff Vorteile> gegenuber plain C bringt.
Und dann bitte ein einziges Beispiel, wie man mit einer Spülmaschine
nach dem Verzehr einer einzelnen Pizza das Geschirr schneller sauber hat
als wenn man von Hand spült.
Wobei der Hauptvorteil von C++ natürlich nicht darin liegt, besseren
Code zu erzeugen, sondern besseren/strukturierteren/wartbareren/...
Quelltext ermöglicht, im Bestfall ohne Nachteile bzgl. Effizienz.
Insofern ist "kein besserer Code" noch kein Argument gegen C++.
Marc Vesely schrieb:> cplusplusser schrieb:>> Nach diesem Thread noch sowas zu behaupten, finde ich eine schlichte>> Frechheit. Immerhin wurden genügend Beispiele gebracht, wo C++ auch für>> Bitte um ein einziges Beispiel wo C++ beim Hardwarezugriff Vorteile> gegenuber plain C bringt.
Klaus Wachtler schrieb:> Insofern ist "kein besserer Code" noch kein Argument gegen C++.
Ich habe nichts gegen C++, aber...
cplusplusser schrieb:> Wo ich aber an meine Grenzen komme: Etwas hardwarenahes zu schreiben und> trotzdem der C++-Philosphie treu zu bleiben.
Was für Philosophie ?
Hardwarenah heisst vor allem, dass der C++ Code nicht einmal zwischen
M8 und M32 portabel ist, mit XMEGA und Tiny will ich gar nicht erst
anfangen.
Also ist das ganze Gelabber von C++ und Hardwarenah oder Portabel von
Anfang an Unsinn.
Weder Assembler, noch C und erst Recht der C++ sind auf Hardwareebene
portabel, Schluss, Ende.
Also, C++ dort benutzen, wo es wirklich Sinn hat und natürlich hat da
niemand etwas dagegen, weder gegen C++ noch gegen seine Anwendung.
Aber eine höhere Sprache mit Gewalt in Bereiche zwingen, wofür die
überhaupt nicht gedacht war und dann auch noch lauthals verkünden:
Ich habe das Rad neu erfunden, mein C++ Code macht fehlerlos das,
wofür es gar nicht gedacht war.
Dass man dasselbe auch in plain C oder sogar noch besser in Assembler
schreiben könnte, ist ja unwichtig.
Natürlich kommt kein normaler Mensch auf die Idee, irgendetwas
kompliziertes im Assembler zu schreiben, warum ist für TO der
umgekehrte Fall normal ?
Und dann denke ich verkehrt...
Marc Vesely schrieb:>> class ScopedInterruptGuard {>> Vorteil gegenüber plain C ?
Viel besser lesbar. Sofort klar, was passiert. Der Guard wird
automatisch wieder entfernt. Kein Risiko eines Resource Leaks.
Finde ich ein sehr schönes Beispiel! Man kann genau das schreiben, was
man auch denkt, nämlich: "Dieser Codeabschnitt muss von einem Guard
geschützt werden."
Marc Vesely schrieb:> Hardwarenah heisst vor allem, dass der C++ Code nicht einmal zwischen> M8 und M32 portabel ist, mit XMEGA und Tiny will ich gar nicht erst> anfangen.>> Also ist das ganze Gelabber von C++ und Hardwarenah oder Portabel von> Anfang an Unsinn.>> Weder Assembler, noch C und erst Recht der C++ sind auf Hardwareebene> portabel, Schluss, Ende.
Das ist einfach quatsch. Das Beispiel mit dem Guard zeigt es doch schon:
In C++ kannst du diesen Guard als Template für jeden Prozessortyp, den
du brauchst, spezialisieren. Im restlichen Code hingegen kannst du den
Guard immer auf die genau gleiche komfortable Art und Weise verwenden.
apr schrieb:> gegenuber plain C bringt.> class ScopedInterruptGuard {> public:> ScopedInterruptGuard()> {> reg = SREG;> ...> // atomic block> ScopedInterruptGuard atomic;> […]> }
Schönes Beispiel. So was nehme ich auch immer wieder gern in Threads
oder Task die untereinander über Mutexe verriegelt sind. Die Methoden an
beliebiger Stelle mit return verlassen zu können ohne sich ums Aufräumen
kümmern zu müssen hat schon seinen Charme.
Marc Vesely schrieb:> cplusplusser schrieb:>> In C++ kannst du diesen Guard als Template für jeden Prozessortyp, den>> du brauchst, spezialisieren.>> LOL.
Soso. Dann erzähl doch mal, wie du sowas portierbar löst.
Ralf G. schrieb:> ATOMIC_BLOCK(ATOMIC_FORCEON)
Das mag für dieses eine Beispiel zutreffen. Aber auch nur genau dafür.
Es ging hier um eine beispielhafte Technik und nicht mehr. Ich glaube
nicht das das Beispiel dazu dienen sollte C++ als die überlegene Sprach
raus zu stellen. Wenn du das vergleichst solltest du aber auch die
#ifdef-Orgie aus der atmic.h in den Vergleich einbeziehen.
cplusplusser schrieb:>>> In C++ kannst du diesen Guard als Template für jeden Prozessortyp, den>>> du brauchst, spezialisieren.>>>> LOL.>> Soso. Dann erzähl doch mal, wie du sowas portierbar löst.
LOL.
Sage ich doch die ganze Zeit, dass so etwas Hardwarenahes eben
nicht portierbar ist.
Der guard ist zwar schön und gut. Aber hardwarenah ist er nicht
wirklich.
Die Funktionen disable_int, getSREG und derSREG sind das. Und wie du
selbst sagst, die müssen neu geschrieben werden.
Dass c++ funktioniert bestreitet niemand nur eben nicht so wie es sich
hier manche wünschen.
temp schrieb:> die #ifdef-Orgie
Gut, die #ifdef-Orgie ist jetzt etwas länger, als die Guard-Klasse.
Ralf G. schrieb:> cplusplusser schrieb:>> Finde ich ein sehr schönes Beispiel!
Darauf hatte ich mich bezogen.
Ralf G. schrieb:> cplusplusser schrieb:>> Finde ich ein sehr schönes Beispiel!>> Ich komme auch damit gut klar: ATOMIC_BLOCK(ATOMIC_FORCEON)> {> ...> }
... was aber kein plain C ist, sondern eine gcc extension
Marc Vesely schrieb:> Also ist das ganze Gelabber von C++ und Hardwarenah oder Portabel von> Anfang an Unsinn.>> Weder Assembler, noch C und erst Recht der C++ sind auf Hardwareebene> portabel, Schluss, Ende.
in dem sinne ... muss man recht geben
das ist wohl wahr ...
wenn man das allein auf die µC interne peripherie begrenzt
ist das
1: meist nie portabel
2: muss man eh immer neu machen ( siehe "BSP" )
allein die register vom AVR unterscheiden sich teils doch schon ...
der eine TIMSK der andere TIMSK1 usw ...
sicher kann man sowas mit präprozessoranweisungen abfangen ..
aber je mehr µC typen dazukommen desto verwirrender
im grunde ist das aber möglich ...
wenn man aber wie weiter oben gesagt eh eine echte applikation laufen
hat,
ist es egal ob man die Hardwarenahen I/Os in ASM, C oder C++ schreibt
man wird sich für das entscheiden was man eh am besten kann bzw sich
nach dem rest richten... bzw inline ASM schreiben
Marc Vesely schrieb:> cplusplusser schrieb:>>>> In C++ kannst du diesen Guard als Template für jeden Prozessortyp, den>>>> du brauchst, spezialisieren.>>>>>> LOL.>>>> Soso. Dann erzähl doch mal, wie du sowas portierbar löst.>> LOL.> Sage ich doch die ganze Zeit, dass so etwas Hardwarenahes eben> nicht portierbar ist.
Natürlich ist der direkte Hardwarezugriff nicht portierbar. Genau
deshalb baut sich ja jeder vernünftige Programmierer eine Abstraktion
über der Hardware-Schicht. Und mit C++ kann man das, wie gezeigt wurde,
sehr elegant lösen. Aber du schreibst vermutlich lieber den gesamten
Code neu.
husten schrieb:> wenn man aber wie weiter oben gesagt eh eine echte applikation laufen> hat, ist es egal ob man die Hardwarenahen I/Os in ASM, C oder C++> schreibt> man wird sich für das entscheiden was man eh am besten kann bzw sich> nach dem rest richten... bzw inline ASM schreiben
Und genau das wäre der größte Fehler den man machen kann um seinen code
portabel zu halten.
Wichtig ist es, die Hardware von der Software zu trennen und das geht am
besten durch kleine hardwarenahe c Funktionen, die auf jedem Controller
den gleichen definierten Namen und die gleiche Funktion haben. Z.b. Ein
i/o pin setzen.
Ähnlich wie bei einem Betriebssystem wird dadurch unabhängig von der
Hardware eine gleiche basis geschaffen. Der code bleibt portierbar und
was der Compiler davon inlined oder nicht kann eigentlich egal sein.
Als erfahrener Programmierer finde ich, dass sich C# am besten für uCs
eignet. Alles hübsch portierbar, super effizient. Bald gibts C##, dass
ist dann einfach noch besser. Natürlich auch für Mikrocontroller.
gcc-extension schrieb:> ... was aber kein plain C ist, sondern eine gcc extension
Da ist mir wohl ['sei()'], 'cli()' und 'SREG' in der
C++-Standard-Bibliothek glatt durch die Lappen gegangen.
apr schrieb:> reg = SREG;> cli();
Ralf G. schrieb:> Da ist mir wohl ['sei()'], 'cli()' und 'SREG' in der> C++-Standard-Bibliothek glatt durch die Lappen gegangen.
Ja, ich muss wohl dieselben Lappen benutzt haben.
Marc Vesely schrieb:> Ralf G. schrieb:>> Da ist mir wohl ['sei()'], 'cli()' und 'SREG' in der>> C++-Standard-Bibliothek glatt durch die Lappen gegangen.>> Ja, ich muss wohl dieselben Lappen benutzt haben.
Also bitte... sei() und cli() als SREG |= 0x80 bzw. SREG &= ~0x80 zu
implementieren, ist wohl noch schaffbar? (jeweils angepasst an den
verwendeten controller)
Und SREG ist ja nun nichts anderes als DDRn - ein define.
Marc Vesely schrieb:> Und nun mach mal dasselbe für verschiedene Register, Bitnamen,> alle XMEGAs, verschiedene MEGAs, alle TINYs, usw...
Wenn du eine Library für verschiedene AVRs schreibst, dann lässt sich
das wohl kaum vermeiden. Oder wie würdest du es angehen?
cplusplusser schrieb:> Marc Vesely schrieb:>> Und nun mach mal dasselbe für verschiedene Register, Bitnamen,>> alle XMEGAs, verschiedene MEGAs, alle TINYs, usw...>> Wenn du eine Library für verschiedene AVRs schreibst, dann lässt sich> das wohl kaum vermeiden. Oder wie würdest du es angehen?
Eben, wo ist HIER der unterschied zwischen C, C++ und ASM oder
irgendeiner anderen Sprache?
gcc-extension schrieb:> Eben, wo ist HIER der unterschied zwischen C, C++ und ASM oder> irgendeiner anderen Sprache?
Eben. Auf der untersten Ebene musst du diese "Wrapper" sowieso von Hand
erstellen, egal ob mit C, C++ oder Assembler. Wenn du dir aber mal einen
C oder C++ Wrapper gebaut hast, so kannst du danach auf einer höheren
Abstraktionsebene dein Programm aufbauen.
Gerade bei "größeren" eingebetteten Systemen (ARM, PowerPC) oder der
Verwendung von Peripheriebausteinen hat der höhere Abstraktions- und
Wiederverwendungsgrad von C++ seine Vorteile.
Wenn man seine Klassenhierarchie z.B. für I2C-Bausteine sauber aufgebaut
hat, ist die Wartung oder das Hinzufügen neuer Bausteine recht leicht,
kann man doch dann auf bewährte Grundlagen aufbauen und muß nicht
jedesmal bei Null anfangen.
Wenn ich z.B. eine Basisklasse I2CGeraet habe, welche ich nur mit der
Adresse initialisieren muß und welche mir Methoden für
(Endianess-abhängige) Datentransfers von/zu Registern verschiedener
Weite (Templates!) anbietet, dann ist die Implementierung einer
konkreten Bausteinunterstützung schon bedeutend leichter.
Habe ich dann noch abgeleitete Basisklassen für z.B. GPIO-Chips, dann
habe ich z.B. den Einzelbitzugriff auch schon für alle Ableitungen
implementiert.
Verwende ich abstrakte Schnittstellen z.B. für Temperatursensoren, dann
kann ich über diese Schnittstelle eine Liste von allen
Temperatursensoren unabhängig vom Bussystem (I2C, SPI, integriert)
aufbauen und diese einheitlich abfragen.
Zu guter Letzt bieten mir Ausnahmen die Möglichkeit, konkrete
Fehlermeldungen "aus den Tiefen des System" nach oben zu bringen und
individuell darauf zu reagieren - welche Ebene dies betrifft, ist damit
offengelassen.
Eine Fehlermeldung wie "Ausgabefehler beim Schreiben auf den DAC
"dac_ort": Ausgabefehler beim Schreiben auf das I2C-Gerät "Selektor2"
(Typ: Selektor ..., Adresse 0x2E, Bus i2cbus3)" hilft beim Zusammenbau
und der Wartung mehr als ein ErrorCode EA-Fehler.
Aber auch auf kleinen AVR's kann man von der Kapselung profitieren.
Mittels der neuen constexpr-Konstruktoren könnte man ohne jegliche
Makroberechnung z.B. die Initialisierung für die Baudratenregister
berechnen und so eine Schreibweise anbieten:
SerialConnection ser1(9600,Parity::none,StopBit::none);
ser1 << "Hallo, Welt!" << endl;
Mir war im Verlauf folgende Formulierung aufgefallen:
>Aber schau, als freier Bastler arbeitet man anders. Nämlich absolut>lösungszentriert. Da ist zum einen der schnellste Weg wichtig.
Was bedeutet der schnellste Weg?
Ich habe jetzt mein erstes Hardwarenahes Projekt in C++ auf einem stm32
laufen und mache ausgiebig gebrauch von Interfaces in Zusammenhang mit
Polymorphy. Hintergrund ist, dass es in dem Design "Piplines" gibt, in
die sich Berechnungsmodule "einhängen" lassen. Diese Module hören alle
auf das selbe Interface und werden daher auch über eine Variable von
diesem Interfacetyp behandelt.
Warum?
Weil ich erstmal einen Satz an grundlegenden Modulen implementiert habe
und noch nicht weiß, was zukünftige können sollen. Durch den
Polymorphismuss ist das aber egal. Natürlich hat das ausdenken des
Konzeptes länger gedauert, als einen Satz Module fix runter zu
programmieren. Aber zukünftig spart es Zeit, weil Plug and Play und ich
muss bestehendes nicht anfassen und wieder debuggen.
Ich will nicht behaupten, dass sich das nicht auch in C machen lässt.
Bin nicht der ultra Crack, der genau weiß, was alles mit
Funktionspointern machbar ist. So gesehen bin ich an einer "C-Version"
des oben Beschriebenen interessiert.
Eine Sache, die immer sinnvoll ist, ist ein File zu haben (z.B. Board.h)
in dem alles oder möglichst viel definiert wird, was mit der Hardware zu
tun hat und diese Zeilen dann über Macros greifbar zu machen.
In der eigentlichen Applikation tauchen dann diese Makros auf, die am
besten alle, Alle, ALLE in dieser Board.h zu finden sind und dort bei
Portierung ZENTRAL angepasst werden können.
Die Guardklasse war nur ein konkretes Beispiel für etwas, was C++ sehr
gut kann: Ressourcen verwalten. Aber ich sehe schon, euch gefällt das
Beispiel nicht. Wie wäre dann so etwas:
Das Problem wird sein: wer C++ haßt, der wird noch nicht mal verstehen
was er da sieht. Was soll er also dazu sagen. Wie soll er die Eleganz
deine "BlockGuard"-Klasse verstehen. Wo er doch noch die PUSHs und POPs
ausbalanciert, wenn noch ein Register für eine kleine Erweiterung einer
Berechnung braucht. Sogar bei nur Blinken muß man sich mit
1
#include<avr/io.h>
2
#include<util/delay.h>
3
4
#define LEDPIN PINB
5
#define LEDDDR DDRB
6
#define LEDBIT 4
7
8
intmain(){
9
LEDDDR|=(1<<LEDBIT);
10
11
while(1){
12
LEDPIN=(1<<LEDBIT);
13
_delay_ms(500);
14
}
15
}
keine Gedanken über viel kleine Details machen, daß ich nie auf die Idee
käme, dazu ASM zu benutzen. Warum auch? Wo reichen Performance und Platz
nicht aus. Nur werde in es keinem ausreden, der sich unbedingt quälen
will. Ok, ist nur C, aber eben kein ASM mehr.
Mit C++ Templates kann man schön so Dinge wie Ring-Puffer bauen,
Elementtyp konfigurierbar, Länge konfigurierbar, Länge bestimmt
automatisch den Typ der In/Out-"Ptr", diese benutzen ein Modulo Template
für den automatischen Wrap around bei Operator ++, Ausgaben in Streams,
die Kommandos ala ANSI (gotoxy, up, down, left, right, clear, home)
verstehen und als Templateparameter die Uart- oder die 16x2 LCD Klasse
mitbekommen.
Usw, usw. Wer nicht versteht was ich schreibe, der wird auch nicht
wissen, wozu das gut ist!
Bastler schrieb:> Usw, usw. Wer nicht versteht was ich schreibe, der wird auch nicht> wissen, wozu das gut ist!
Richtig.
Der Mist wird immer komplizierter, je mehr "abstrahiert" wird. Das ist
DAS, was ich verstehe.
apr schrieb:> Die Guardklasse war nur ein konkretes Beispiel für etwas, was C++ sehr> gut kann: Ressourcen verwalten. Aber ich sehe schon, euch gefällt das> Beispiel nicht. Wie wäre dann so etwas:> [code]> struct CNT1 {> static constexpr volatile uint8_t &low() { return TCNT1L; }> static constexpr volatile uint8_t &hi() { return TCNT1H; }> };>> template<class Trait>> class Access16Bit
Aha.
Dasselbe in Assembler:
1
;*ErstmalsehenumwelcheRegisteressichhandelt...
2
.macroStore;Register,Address
3
.if@0>0x3F
4
sts@0,@1
5
.else
6
out@0,@1
7
.endif
8
.endmacro
9
10
.macroLoad;Register,Address
11
.if@1>0x3F
12
lds@0,@1
13
.else
14
in@0,@1
15
.endif
16
.endmacro
17
18
;*JetztkommendieTemplates...
19
.macroGet16bit
20
LOADMacReg,@0H
21
mov@1H,MacReg
22
LOADMacReg,@0L
23
mov@1L,MacReg
24
.endmacro
25
26
.macroPut16bit
27
ldiMacReg,High(@1)
28
STORE@0H,MacReg
29
ldiMacReg,Low(@1)
30
STORE@0L,MacReg
31
.endmacro
32
33
34
;*Unddannimmain...
35
36
Get16bitTCNT1,Z
37
Put16bitTCNT1,0x1234
Schätze, ungefähr 10:1 Effizienz mindestens.
Bin natürlich nicht gegen C++, aber bitte nur dort, wo es auch Sinn
hat.
Bastler schrieb:> Usw, usw. Wer nicht versteht was ich schreibe, der wird auch nicht> wissen, wozu das gut ist!
Wie wäre es, wenn du erst mal selber etwas mehr über C++ lernst ?
Das C Beispiel war dazu da, zu zeigen, daß auch (oder gerade)
einfachstes besser in Hochsprachen gemacht wird. Und richtig! meine DCOM
Programme mit der Active Template Lib liegen schon mehr als 10 Jahre
zurück, Geld verdien ich heute mit ganz anderen Sprachen und als Hobby
bastle ich eben an den Dingen, die ich oben beschrieben hab. Nur
verstehen tut's nicht jeder. Stand da auch schon. Im übrigen: zofft euch
mit euch selbst!
apr schrieb:> jo. Access16Bit<CNT1> tcnt1;> tcnt1 = 0x1122;> ldi r24,lo8(17)> out 0x2d,r24> ldi r24,lo8(34)> out 0x2c,r24> uint16_t foo = tcnt1;> in r24,0x2c> in r18,0x2d
LOL.
Und jetzt mach das mal mit OCR1A und OCR1B.
Ich brauche nur zu schreiben:
Put16bit OCR1A, 0x1234
Oder:
Get16bit OCR1B, Y
Und Ihr, C++ Gurus ?
Marc Vesely schrieb:> Schätze, ungefähr 10:1 Effizienz mindestens.
10:1 Effizienz gemessen nach was? Man kann davon ausgehen, dass der
Compiler das genau so gut optimiert, wie du es in Assembler schreiben
kannst. Lesbarer ist es auch nicht, eher weniger. Flexibler schon gar
nicht.
Unwissender schrieb:> LOL.> Und jetzt mach das mal mit OCR1A und OCR1B.>> Ich brauche nur zu schreiben:> Put16bit OCR1A, 0x1234> Oder:> Get16bit OCR1B, Y>> Und Ihr, C++ Gurus ?
Hier interessiert sich auch niemand (ausser Moby) dafür, Trivialaufgaben
mit möglichst wenig Code zu erledigen. Es ging von Anfang an darum, wie
man mit C++ eine gute Abstraktion über die Hardware legen kann. Zunächst
ist das immer mit mehr Schreibarbeit und mehr Komplexität verbunden.
P. M. schrieb:> Hier interessiert sich auch niemand (ausser Moby) dafür, Trivialaufgaben> mit möglichst wenig Code zu erledigen.
... und noch für sehr viel mehr. Da wird dann erst richtig Code gespart
und man kommt weiter mit nem AVR statt ARM über die Runden. Das ist
einem überzeugten OOPlogen natürlich schlecht zu vermitteln...
> ist das immer mit mehr Schreibarbeit und mehr Komplexität verbunden.
Richtig! Ich wünsch Euch, Ihr habt nach Projektende trotzdem noch das
Gefühl, es hat sich gelohnt. Nicht den intellektuelle Spaß, die
Effizienz meine ich ;-)
apr schrieb:> Die Guardklasse war nur ein konkretes Beispiel für etwas, was C++ sehr> gut kann: Ressourcen verwalten. Aber ich sehe schon, euch gefällt das> Beispiel nicht.
Ich glaube eher, es wurde nicht verstanden, um was es eigentlich geht.
Ralf G. schrieb:> gcc-extension schrieb:>> ... was aber kein plain C ist, sondern eine gcc extension>> Da ist mir wohl ['sei()'], 'cli()' und 'SREG' in der> C++-Standard-Bibliothek glatt durch die Lappen gegangen.>> apr schrieb:>> reg = SREG;>> cli();
Es geht doch hier gar nicht um das SREG selbst, sondern vielmehr um die
Art, wie es verwaltet wird. Das SREG ist da nur ein Beispiel.
Prinzipiell läßt sich jede beliebige Ressource auf die gleiche Weise
handhaben. Einen vergleichbaren Automatismus gibt es in C nicht, deshalb
wurde im GCC die unportable Krücke mit dem ATOMIC_BLOCK eingebaut.
Mir scheint, in gewisser Weise durch die Namensgebung des Threads
provoziert wird C++ verstärkt von Seiten der Initialisierung und des
"Wertabholens" betrachtet. Je nachdem was man macht, ist das aber nur
der kleinste Teil.
Bei dem was ich aktuell mache halte ich C++ für sinvoll. Letztlich lese
ich nur ein paar Analogwerte ein und frage ein paar digitale Pins ab.
Das was ich damit mache findet in Zeitfenstern statt, in denen sich der
µC hochgradig langweilt.
Wenn ich dabei währe und müsste schnell laufende Filter/Regelungen
entwerfen, sähe die Welt vielleicht anders aus. Da den
"Entscheidungsthreshold" zu finden, brauchts mehr als meine Erfahrung...
robin schrieb:> husten schrieb:>> wenn man aber wie weiter oben gesagt eh eine echte applikation laufen>> hat, ist es egal ob man die Hardwarenahen I/Os in ASM, C oder C++>> schreibt>> man wird sich für das entscheiden was man eh am besten kann bzw sich>> nach dem rest richten... bzw inline ASM schreiben>> Und genau das wäre der größte Fehler den man machen kann um seinen code> portabel zu halten.>> Wichtig ist es, die Hardware von der Software zu trennen und das geht am> besten durch kleine hardwarenahe c Funktionen, die auf jedem Controller> den gleichen definierten Namen und die gleiche Funktion haben. Z.b. Ein> i/o pin setzen.>> Ähnlich wie bei einem Betriebssystem wird dadurch unabhängig von der> Hardware eine gleiche basis geschaffen. Der code bleibt portierbar und> was der Compiler davon inlined oder nicht kann eigentlich egal sein.
ja .. in dem sinne meinte ich das ja auch ...
die applikation sollte von eigentlichen I/O losgelöst sein ...
ich habe dazu funktionszeiger im einsatz... zum setzen oder löschen
rufen die eine callbackfunktion auf. das ist der selbe weg wie eine
funktion für setzen/löschen global zu definieren.
nur das ich bei der init eben diesen *FP mit angebe .. was dann in der
funktion steht ... also ein einfaches PORT |=(1<<1); oder etwas
komplexeres weil mehrere register beshrieben werden müssen ist dabei
egal
ich brauche aber die set/get funktionen nicht global bekantgeben...
und kann so je nach aufgabe auch einen wrapper schreiben der eine
zwischenschicht darstellt ..
ja ich weiß .. sowas geht über ein simples sbi.. hinnaus :-(
aber so komm ich prima klar
ich brauche je nach µc nur eine hand voll set/get funktionen ( quasi BSP
)
dann läuft die software
Moby schrieb:> ... und noch für sehr viel mehr. Da wird dann erst richtig Code gespart> und man kommt weiter mit nem AVR statt ARM über die Runden.
Das ist ja genau der Punkt, der bereits widerlegt wurde: C++ generiert
gar nicht grösseren Binärcode.
P. M. schrieb:> Hier interessiert sich auch niemand (ausser Moby) dafür, Trivialaufgaben> mit möglichst wenig Code zu erledigen. Es ging von Anfang an darum, wie> man mit C++ eine gute Abstraktion über die Hardware legen kann. Zunächst> ist das immer mit mehr Schreibarbeit und mehr Komplexität verbunden.
Es ging mir eher darum, zu zeigen wie sinnlos das Ganze ist.
Ich programmiere nur noch selten in Assembler und für Hardware wird
bei mir sowieso eine Library benutzt.
Da ich zufälligerweise einen PC habe und auf diesem auch zufällig
VS2010 installiert ist, hatte ich auch die Gelegenheit mit C++ etwas
mehr als 'hello world' zu produzieren.
Dann kam ich auf die komische Idee, die XML files von ATMEL zu nutzen
um gewisse Hardwarefunktionen nicht mehr von Hand schreiben zu müssen.
Und dazu habe ich C++ ausprobiert und siehe da - es funktionierte.
Jetzt läuft auf dem PC einen Programm mit etwa 2MB aber mit SQL,
grafischer Oberfläche, da kann man Prozessortyp, Geschwindigkeit,
benötigte Timer, ADC, SPI, USART etc. schön auswählen, die
dazugehörigen Register werden auch komischerweise alle angezeigt.
Eine andere komische Idee von mir war, per Click auszuwählen, ob ein
komplettes Programmgerüst oder nur eine Funktion erzeugt werden sollte.
Und am komischsten fand ich die Idee, dass man mit noch einem Click
auswählen kann, ob das Ganze als Library-Function geht oder ob nur ein
Code-Snippet erzeugt werden sollte.
Jetzt kann ich mit ein paar clicks für irgendeinen X-beliebigen AVR
ein Programm erzeugen mit allem was dazugehört, also mit #includes,
Init_xxx(), ISR, main() und vor allem die ganzen #define und #ifdefs
werden richtig in eine Def_xxx.h reingeschrieben. Sogar die Kommentare
gehen automatisch rein.
Was auch sehr komisch ist:
Ich brauche diesen Prozessortyp gar nicht mal zu kennen - alles
nötige steht in XML files, man muss nur wissen wie das alles zu
verwenden ist.
Dass C++ auch auf uC geht, steht ausser Frage, nur sollte man
C++ das machen lassen, wofür der auch geschrieben wurde.
Die ganze PiPaPo Arbeit mit der Hardware kann man viel besser
irgendwo anders (auf dem PC) erledigen. Auch sind die Möglichkeiten
einen dummen Fehler mit falscher Bitbezeichnung oder so zu machen,
damit (fast) ausgeschlossen.
Rüdiger Knörig schrieb:> Verwende ich abstrakte Schnittstellen z.B. für Temperatursensoren, dann> kann ich über diese Schnittstelle eine Liste von allen> Temperatursensoren unabhängig vom Bussystem (I2C, SPI, integriert)> aufbauen und diese einheitlich abfragen.
Ja, nur geht das auch in plain C (fast) genauso einfach. Und wrapper
dazu schreibt der Programm auf dem PC (fast) von alleine.
Nur ist es eben unnötige Arbeit, da ist mit C++ natürlich das Leben
viel einfacher.
Es ist in etwa so wie mit CAN und verschiedenen Layers.
Kein normaler Mensch fährt CAN mit bitbanging.
Warum sollte C++ das tun ?
Marc Vesely schrieb:> Es ging mir eher darum, zu zeigen wie sinnlos das Ganze ist.> Ich programmiere nur noch selten in Assembler und für Hardware wird> bei mir sowieso eine Library benutzt.
Sinnlos ist es nur für den, der es, weil er die Vorteile nicht kennt,
nicht benutzt.
Und ein Vorteil von Libraries als Template-Sammlung (da braucht man aber
leider C++) ist, daß man (notfalls per LTO) eine über-Alles-Optimierung
bekommt.
Wieviele Versionen von Library gibt es denn für die verschiedenen AVR's.
Für jeden eine, oder eine, die zur Laufzeit entscheidet ob der Port im
IO- oder MEM-Bereich liegt.
ASM hab ich benutzt, als es keine bezahlbaren Compiler gab. Anfangs
gab's noch nicht mal Assembler in bezahlbar, da wurde eben
hand-assembliert. C seit ich welche für umme bekommen konnte (was die
Hersteller nicht immer so geplant hatten) und C++ seit das Vorteile
bringt.
andersdenkender schrieb:> Wieviele Versionen von Library gibt es denn für die verschiedenen AVR's.> Für jeden eine, oder eine, die zur Laufzeit entscheidet ob der Port im> IO- oder MEM-Bereich liegt.
Wie gesagt, steht alles in XML:
Marc Vesely schrieb:> Dass C++ auch auf uC geht, steht ausser Frage, nur sollte man> C++ das machen lassen, wofür der auch geschrieben wurde.> Die ganze PiPaPo Arbeit mit der Hardware kann man viel besser> irgendwo anders (auf dem PC) erledigen.
Und genau das tut der Compiler auf dem PC für dich, wenn du z.B.
Templates verwendest.
So lange man keine virutelle Vererbung und keine verrückten Sachen aus
std verwendet, kann man jedes C++-Programm straight-forward in ein
C-Programm verwandeln. Von dort aus gehts wiederum einfach nach
Assembler. Macht natürlich netterweise alles der Compiler für dich. Da
es so einfach ist, hat er auch keine Mühe, daraus genau so guten Code zu
erzeugen, als wäre es C. Und ein gut optimertes C-Compilat schlägt man
von Hand in Assembler nicht so schnell.
Hat also nur Vorteile: Der Programmierer kann in hoher Abstraktion
denken und schreiben, während der Compiler dafür sorgt, dass es in ein
hocheffizientes Programm umgesetzt wird.
Noch am Rande: C++ wurde im Gegensatz zu anderen höheren
Programmiersprachen ja auch gezielt für eine hocheffiziente low-level
Implementierung designt. Und zwar damals auf Rechnern, die heute nicht
mal mit einem AVR mithalten können.
Rolf Magnus schrieb:> deshalb> wurde im GCC die unportable Krücke mit dem ATOMIC_BLOCK eingebaut.
Ah ja. Ein Beitrag zum Thema Portabilität der Hochsprache.
P. M. schrieb:> Und ein gut optimertes C-Compilat schlägt man> von Hand in Assembler nicht so schnell.
Entschuldigung, Unfug. Wenn man nur halbwegs gut die Möglichkeiten
"seines" Controllers nutzt und in Asm halbwegs fit ist! Aber: Bei
Programmen ab einer gewissen Größenordnung mag die Konzentration des
Programmierers nachlassen ;-)
Irgendwer schrieb:> Da könnte einem schon der Verdacht> kommen das beim Thema Optimierung zumindest beim gcc noch einiges an> Luft für Verbesserungen vorhanden ist.
Schau einer an. Aber man kann ja immer noch ein paar Hundert bis Tausend
Euro in einen "ordentlichen" Compiler stecken, ich weiß schon. Der läuft
dann natürlich auch konfigurations- und fehlerfrei und weiß für seine
Optimierungen stets intelligent den Code-Sinn zu interpretieren.
Marc Vesely schrieb:> Dass C++ auch auf uC geht, steht ausser Frage,Christian Berger schrieb:> Also mir wäre noch nie ein Fall untergekommen, wo man einen µC in C++> programmiert hätte
Dazu wär wirklich mal eine Umfrage interessant.
Meine Vermutung: Sie würde für C++ vernichtend ausfallen.
P. M. schrieb:> Hat also nur Vorteile: Der Programmierer kann in hoher Abstraktion> denken und schreiben,P. M. schrieb:> Das ist ja genau der Punkt, der bereits widerlegt wurde: C++ generiert> gar nicht grösseren Binärcode.
In abstrakter Theorie vielleicht. In der Praxis liegt der Teufel stets
im Detail. Bei richtiger Initialisierung aller Register, mindestens
halboptimaler Nutzung der Peripherie, Interruptsystem, Event-Netzwerk,
1:1 Umsetzung der Funktionalität und vorgesehener, schon lang (selbst)
optimierter I/O-Methoden nie und nimmer! Aber gut, das kann der pure C++
Programmierer wohl gar nicht wissen. Ist zu sehr auf abstraktes Denken
festgelegt. Hochfliegend mit einer gewissen unscharfen Übersicht über
die Landschaft, aber ohne (hardwarenahen) Bodenkontakt und in steter
Absturzgefahr ;-)
Ret schrieb:> C++> Protagonisten verführen regelrecht gewollt oder ungewollt mit ihrem> fortwährenden Betonen ihrer "Überlegenheitskultur" gegenüber anderen> Programmiersprachen andere dazu, sich auch in C++ zu probieren. Der Ball> wird dann prompt gerne aufgenommen. Man will schließlich auch irgendwie> zur "C++ Elite" dazugehören. Dann aber stechen die Nebenwirkungen und> Begleiterscheinungen aus dem (C++)-Beipackzettel beim Probanden immer> mehr durch. Ergebnis: Dass gerade daraus dann vielleicht umso mehr> fehlerhafte und gar nicht immer so Effizient wie behauptet Programme> erwachsen, weil kaum einer dieses Thema richtig beherrscht, steht dem> ganzen schönen Thema C++ hässlich gegenüber, wird aber gerne unter den> Teppich gekehrt, weil die Wenigsten freiwillig und offen zugeben, dass> sie ihr C++ eben nicht so richtig oder bisweilen sogar gar nicht> beherrschen. REAL werden dann eher die gewohnten C-Programme> geschrieben, durch den C++ Compiler geschickt und heraus kommt sowas wie> .. C+.
Soviel zum psychologischen Aspekt der Sache.
Christian Berger schrieb:> Irgendwie bestätigt das mich in meinem Glauben, dass es auf der Welt> vielleicht 100 Leute gibt, die C++ wirklich können.
Und mich in meinem, wie empfehlenswert es sein muß, die viele Zeit
aufzubringen dieses C++ "Baumaterial" in Perfektion zu erlernen ;-)
Möchte auch mal einen Vergleich bringen: Mit viereckigen Steinen lassen
sich zweifellos große und komplizierteste Gebäude bauen. Warum aber
haben die Steine wohl so eine einfache Form?
A. K. schrieb:> Ich finde C++ eine ziemlich grässliche Konstruktion - übrigens von> Anfang an seit der Lektüre des ersten Stroustrup. Kann nicht anders> sein, da schon C schaurig geraten ist und nie für die Dimension gedacht> war, in der es heute eingesetzt wird. Aber das ist Philosophie auf der> Wiese. Das Zeug ist nun einmal da.
... und muß wohl nun auf Teufel komm raus genutzt werden. Aber nicht vom
freien Bastler ;-)
Alle Zitate übrigens vom Nachbarthread
Beitrag "Was ein C++-"Guru" so ueber Geschwindigkeit erzaehlt."
der die unkomplizierte, effiziente Anwendung von C++ in der Praxis
wunderbar beleuchtet ;-)
Ich hab das Gefühl, hinter vorgehaltener Hand weiß auch der Letzte
hier, wie schlecht C++ in der Gesamtheit aller Details seiner Anwendung
(gerade bei hardwarenahen Sachen) für einfache bis mittelkomplexe
Projekte geeignet ist. Hört doch endlich auf, den einfachen ehrlichen
Programmierer mit diesem "Zeug" an der Nase herumzuführen. Danke.
Moby schrieb:> Alle Zitate übrigens vom Nachbarthread> Beitrag "Was ein C++-"Guru" so ueber Geschwindigkeit erzaehlt."> der die unkomplizierte, effiziente Anwendung von C++ in der Praxis> wunderbar beleuchtet ;-)
Der Thread hat nichts, aber auch garnichts mit C++ zu tun (davon
abgesehn dass der TO im Titel C++ anstatt C verwendet).
Da du ihn hier trotzdem verlinkt zeigt dass, das du ihn garnicht gelesen
hast (sonst wüsstest du dass es dort um plain C geht).
Fazit: du bist garnicht an einer durch Argumenten fundierten Diskussion
interessiert.
Marc Vesely schrieb:> Wie gesagt, steht alles in XML
Könntest du mal den xml teil von einem hardwaremodul, z.b. Timer1
posten? Bin gerade unterwegs und konnte auf die schnelle nichts finden.
Aber was da noch so alles drin steht hat mich doch neugierig gemacht.
Moby schrieb:> Ich hab das Gefühl, hinter vorgehaltener Hand weiß auch der Letzte> hier, wie schlecht C++ in der Gesamtheit aller Details seiner Anwendung> (gerade bei hardwarenahen Sachen) für einfache bis mittelkomplexe> Projekte geeignet ist
Hier geht es auch nicht um "einfache bis mittelkomplexe" Projekte,
sondern um Projekte von einer Grösse, wo man sich auch Gedanken um
Abstraktionen auf höherer Ebene machen muss. Ich für meinen Teil mache
das bereits bei einfachen Projekten: Zuerst die Struktur verstehen, dann
eine Software-Architektur planen, dann umsetzen. Hat am Anfang einen
gewissen Overhead, dafür funktioniert es meistens dann prächtig und ist
extrem flexibel. Gewisse Leute mögen diesen Ansatz nicht, da man zuerst
vielleicht 2 Stunden bis 2 Wochen "nichts" produziert. Ich hingegen
hasse es, wenn jede Modifikation Handarbeit im gesamten Programm
bedeutet.
le x. schrieb:> Der Thread hat nichts, aber auch garnichts mit C++
Komisch. In jedem Zitat kommt C++ vor ...
le x. schrieb:> das du ihn garnicht gelesen> hast
Stimmt. Die Zitate sind blind herausgepickt.
cplusplusser schrieb:> Hier geht es auch nicht um "einfache bis mittelkomplexe" Projekte,> sondern um Projekte von einer Grösse, wo man sich auch Gedanken um> Abstraktionen auf höherer Ebene machen muss.
Warum hast Du das nicht gleich gesagt? Wo immer diese Sphäre auch
anfangen mag. OK- dann trennen wir uns an dieser Stelle in Frieden. Aber
nicht den Überblick verlieren ;-)
Moby schrieb:> Komisch. In jedem Zitat kommt C++ vor ...
Ja, hier hast du recht. Das ist echt komisch.
Im ganzen Thread geht es nur um plain-C, und ob man besser mittels Index
oder Zeiger ein Array kopiert.
Da C (fast) eine Teilmenge von C++ ist könnte man nun argumentieren dass
alles, was C ist, auch C++ ist.
Aber wir wollen uns ja hier nicht in Spitzfindigkeiten verlieren.
Moby schrieb:> cplusplusser schrieb:>> Hier geht es auch nicht um "einfache bis mittelkomplexe" Projekte,>> sondern um Projekte von einer Grösse, wo man sich auch Gedanken um>> Abstraktionen auf höherer Ebene machen muss.>> Warum hast Du das nicht gleich gesagt? Wo immer diese Sphäre auch> anfangen mag. OK- dann trennen wir uns an dieser Stelle in Frieden. Aber> nicht den Überblick verlieren ;-)
Was soll der Quatsch? In jedem zweiten Posting versucht man dir zu
erklären, dass die Welt nicht nur aus deinem LED-Beispiel besteht und du
konterst damit, es sei ein völlig allgemeingültiges Beispiel. Und jetzt
bist du völlig überrascht, dass es hier um eher etwas grössere Projekte
geht?!?
robin schrieb:> Könntest du mal den xml teil von einem hardwaremodul, z.b. Timer1> posten? Bin gerade unterwegs und konnte auf die schnelle nichts finden.> Aber was da noch so alles drin steht hat mich doch neugierig gemacht.
Steht so ziemlich alles drin, nur eben verteilt im ganzen XML.
Ich hab dir hier etwas handisch und wahllos rausgeschnitten, es ist
einfach zu viel, um alles so rauszusuchen.
Im Prinzip nimmt man zuerst die IO_MODULEs, merkt sich die MODULE_LIST
und klappert dann einen nach dem anderen ab.
Unwissender schrieb:> Und jetzt mach das mal mit OCR1A und OCR1B.>> Ich brauche nur zu schreiben:> Put16bit OCR1A, 0x1234> Oder:> Get16bit OCR1B, Y>> Und Ihr, C++ Gurus ?
Marc Vesely schrieb:> Und in plain C:> ocr1a = 0x1234;> uint16_t y = ocr1a;>> Was ist deiner Meinung nach kürzer und übersichtlicher?
Na wenn der C Compiler das korrekt erzeugt, ist die gesamte Klasse
unnütz, nicht wahr.
Es hat keinen Sinn, den Nutzen von C++ anhand von Trivialbeispielen zu
zeigen. Da wird man immer verlieren. Eher sollte die
Assembler/C-Fraktion mal zeigen, wie sie eine grössere Library
implementiert und dann schauen wir mal, ob das in C++ nicht ein
"bisschen" übersichtlicher und genau so performant geht.
da muss man nur die ASM-FP-Macro-Bibliotek rausholen und schon kann man
das auch. sqrt() und sin() liefern ja double, da kann man dann schon
8er-Pakete Register händisch verwalten. das bringt's ;-)
BTW, wenn ich wemand zwingen würde, das in AVR-ASM zu machen, dann würde
ich mir auf alle Fälle vom GCC ein "ASM-Template" oder auch .lss-File
erzeugen lassen. Oder ich verwend die Zeit darauf den Anforderer in die
richtige Richtung zu schubsen.
le x. schrieb:> Moby schrieb:>> Alle Zitate übrigens vom Nachbarthread>> Beitrag "Was ein C++-"Guru" so ueber Geschwindigkeit erzaehlt.">> der die unkomplizierte, effiziente Anwendung von C++ in der Praxis>> wunderbar beleuchtet ;-)>> Der Thread hat nichts, aber auch garnichts mit C++ zu tun (davon> abgesehn dass der TO im Titel C++ anstatt C verwendet).> Da du ihn hier trotzdem verlinkt zeigt dass, das du ihn garnicht gelesen> hast (sonst wüsstest du dass es dort um plain C geht).>> Fazit: du bist garnicht an einer durch Argumenten fundierten Diskussion> interessiert.
Von C++ hat er doch keinen blassen Schimmer, wie soll er das dann
überhaupt auseinander halten? Wahrscheinlich kann er nicht mal C (zu
komplex, ist immer sein Argument ;) ). Und erzählt dann irgendwas was er
mal so beiläufig aufgeschnappt hat. Insofern kann er an dieser
Diskussion eigentlich nicht teilnehmen.
andersdenkender schrieb:> sqrt() und sin() liefern ja double
Ich sprach von Festkommazahlen.
Durch Überladen von Operatoren kann man sich Berechnungen hinschreiben
wie von ganzen Zahlen oder Gleitkommazahlen gewohnt, in Wirklichkeit
rackern im Hintergrund templates.
Das ist ein Vorteil von C++, an den man mit ASM oder C nicht herankommt.
Selbst in C sehen Berechnungen mit Festkommazahlen ziemlich wüst aus.
Siehe auch Beitrag "Festkommazahlen mit C++"
andersdenkender schrieb:> da muss man nur die ASM-FP-Macro-Bibliotek rausholen und schon kann man> das auch. sqrt() und sin() liefern ja double, da kann man dann schon> 8er-Pakete Register händisch verwalten. das bringt's ;-)
Festkommazahlen? Komplexe Zahlen? Oder wenn man einfach mal eine
spezielle Arithmetik braucht? Es behauptet ja niemand, dass man sowas
mit Assembler nicht gebacken bekommt. Aber du kannst auch nicht
abstreiten, dass die C++-Variante mit Operatorüberladung einfach viel
lesbarer und eleganter daherkommt. Und ein guter Compiler setzt das auch
so um, dass keine Ineffizienz entsteht. Ganz abgesehen davon, dass man
in vielen Fällen gar nicht so auf dem Zahnfleisch läuft, dass man jede
Instruktion zählen muss. Wenn du jede Sekunde einen Sensor auslesen, den
Wert nach einer eher aufwändigen Formel umrechnen und auf ein Display
ausgeben musst, dann hat selbst ein kleiner AVR unendlich
Leistungsreserven und du bist glücklich, die Formel intuitiv
aufschreiben zu können.
> BTW, wenn ich wemand zwingen würde, das in AVR-ASM zu machen, dann würde> ich mir auf alle Fälle vom GCC ein "ASM-Template" oder auch .lss-File> erzeugen lassen. Oder ich verwend die Zeit darauf den Anforderer in die> richtige Richtung zu schubsen.
Ich weiss gar nicht recht, welchen Standpunkt du jetzt vertrittst, aber
wir sind uns wohl einig, dass spätestens hier C++ weniger kompliziert
ist als die Assembler-Lösung?
Klaus Wachtler schrieb:> Durch Überladen von Operatoren kann man sich Berechnungen hinschreiben> wie von ganzen Zahlen oder Gleitkommazahlen gewohnt, in Wirklichkeit> rackern im Hintergrund templates.
Und in Wirklichkeit sorgt das dafür, dass man die Wirklichkeit nicht
mehr sieht. Wenn man nur lange genug raus ist oder in fremden Code
einsteigen muss, bleibt von dem eigentlichen Vorteil nichts mehr übrig.
Ich kann dem exzessiven Überladen von Operatoren überhaupt nichts
abgewinnen. Eine Funktion mit einem aussagekräftigen Namen ist häufig
klar im Vorteil.
Wenn man massenweise Templates verwendet und hinterher erst mal im
Listing nachsehen muss was denn nun dabei rausgekommen ist, wird es
albern. Auf dem PC spielt das heute keine Rolle mehr, aber auf einem
Controller schon.
andersdenkender schrieb:> da muss man nur die ASM-FP-Macro-Bibliotek rausholen und schon kann man> das auch. sqrt() und sin() liefern ja double, da kann man dann schon> 8er-Pakete Register händisch verwalten. das bringt's ;-)P. M. schrieb:> Ich weiss gar nicht recht, welchen Standpunkt du jetzt vertrittst, aber> wir sind uns wohl einig, dass spätestens hier C++ weniger kompliziert> ist als die Assembler-Lösung?
Ich bin hoffentlich nicht der Einzige, der die Ironie in diesen Zeilen
des andersdenkende erkannt hat.
zu Templates und Operator Overloading:
Einmal schreiben (und debuggen) und danach den Compiler die
Routinearbeit machen lassen.
temp schrieb:> Klaus Wachtler schrieb:>> Durch Überladen von Operatoren kann man sich Berechnungen hinschreiben>> wie von ganzen Zahlen oder Gleitkommazahlen gewohnt, in Wirklichkeit>> rackern im Hintergrund templates.>> Und in Wirklichkeit sorgt das dafür, dass man die Wirklichkeit nicht> mehr sieht. Wenn man nur lange genug raus ist oder in fremden Code> einsteigen muss, bleibt von dem eigentlichen Vorteil nichts mehr übrig.> Ich kann dem exzessiven Überladen von Operatoren überhaupt nichts> abgewinnen.
Das Überladen von Operatoren ist dann sinnvoll und überhaupt nicht
verwirrend, wenn dabei die ursprüngliche Bedeutung des Operators
erhalten bleibt.
Ein überladener '+'-Operator sollte also wie das Original immer noch
eine Addition ausführen, nur mit anderen Datentypen, also statt int
oder double bspw. complex oder fixedpoint. Das obige Beispiel von
Klaus stellt somit eine gute Verwendung der Überladung dar.
Denn
1
y=a*b*x+c;
ist einfach um ein Vielfaches besser lesbar als
1
y=fixadd(fixmul(fixmul(a,b),x),c);
Schlecht und verwirrend wäre es hingegen, wenn der '+'-Operator statt
der Summe das Produkt aus zwei Zahlen berechnen würde, was zu einer
völlig falschen Wahrnehmung des Ausdrucks
1
a+b
führte.
Hier sollte – wie an vielen anderen Stellen in der Softwarentwicklung
auch – das Prinzip der geringsten Verwunderung beherzigt werden.
Stroustrup selbst geht da leider mit schlechtem Beispiel voran und
überlädt die Bitshift-Operatoren << und >> mit Funktionen für die
Ein-/ausgabe. Diese haben nicht nur überhaupt nichts mit Bitschieberei
zu tun, sondern weisen zudem noch Nebeneffekte auf. Außerdem liegen die
Operatoren – als Ein-/Ausgabeoperatoren eingesetzt – in der Operator-
rangfolge zu weit oben. So etwas ist einfach Murks, der nur deswegen
akzeptiert wird, weil man sich inzwischen daran gewöhnt hat.
Leider erlaubt C++ nicht die Definiton neuer Operatoren, mit denen
solche Probleme auf saubere Art und Weise beseitigt werden könnten.
Bastler schrieb:> zu Templates und Operator Overloading:> Einmal schreiben (und debuggen) und danach den Compiler die> Routinearbeit machen lassen.
Ja,ja. das Ringbufferbeispiel wird immer gern genommen. Soweit ok. Das
Modulo finde ich schon wieder grenzwertig. Entweder ich mache dann einen
schönen langen sprechenden Variablennamen ala IchBinEinModulo5 oder ich
muss mit Kommentaren dafür sorgen, dass ich immer weiss dass die
Variable x beim ++ nach 5 eine 0 macht. Und alle anderen Konstrukte
dürfen auch nicht falsch zählen. Was macht dann ein x=x+1? Und warum
verhält es sich anders als das ++? Ne, bei aller Liebe. Irgendwo gibt's
ne Grenze. Irgendwann wird es Krampf.
Danke oben für das Beispiel mit >> und <<. Genau dieser Schwachsinn ist
es, der dafür Sorge getragen hat, dass printf und Konsorten die Zeiten
unbeschadet überlebt haben. Das was in der C++ std-Lib an
Stringverarbeitung (auch und vor allem in Versionen ohne! dynamischen
Speicher) vorhanden ist, ist ja wohl nicht der Rede wert.
Ich finde C++ Entwicklung für uC hat nur ein einziges echtes Problem:
Portierbarkeit zwischen unterschiedlichen Compilern. Es gibt exotische
Compiler, es gibt alte Compiler (die man manchmal nutzen muss) - alle
verstehen C aber manche nicht alle C++ Features oder gar nur ein
rudimentäres C++ Subset. C++ Code welcher die Features des neusten
Standards nutzt ist damit erstmal enorm schlecht wiederzuverwenden. Nach
Leidvollen Erfahrungen mit TI (nur C++ Subset) und altem Gcc (kein
Placement-New) setze ich zwar auf objektorientierte Denke aber
implementiere sie meist in C. Wer schonmal große gewachsene Projekte vor
sich hatte weiß, dass "mal eben vorher auf die neuste Compilerversion
updaten" schon ein separates Projekt für sich sein kann und nicht immer
als Lösung in Frage kommt.
Es geht um weiter nichts als um ein 1024 Byte langes Array anzulegen und
zu füllen. Einmal mit den c++ std::vectoren und zum anderen in der von C
gewohnten Art und Weise. Der Code lief im Simulator von Crossworks auf
einem STM32F334. Folgende Ergebnisse im Debugmodus:
1
std::vectorsysticks=86432
2
c-arraysysticks=12352
3
4
undjetztimReleasemode:
5
6
std::vectorsysticks=8253
7
c-arraysysticks=4153
Soviel erst mal zur Effizienz. Bemerkenswert ist auch die über 10fache
Zeit im Verhältnis Debug/Release. Bei der C-Methode ist das mit der
3fachen Zeit nicht ganz so schlimm. Eine Aussage stelle ich deshalb mal
in den Raum: Ein übliches Cortex Mx Programm hat in C++ im Debugmodus
zeitlich mit der Wirklichkeit nicht mehr viel zu tun wenn die std::lib
im Spiel ist. Das erleichtert die Fehlersuchen nicht gerade. Da würde
dann helfen nur gezielte Bereiche des Programms mit Debuginfos zu
versehen. Kontraproduktiv ist dabei in C++, dass viel Programmcode aus
den Headern erzeugt wird.
Jetzt können die Argumente kommen, die Variante mit dem std::vector wäre
viel sicherer. Auch das ist ein Trugschluss. Ein kleiner Fehler wie:
1
for(intn=0;n<=1024;n++)
2
anstelle
3
for(intn=0;n<1024;n++)
hat in der traditionellen Variante das Schreiben über den allocierten
Bereich zur Folge. Mit all seinen bekannten Konsequenzen. Die C++
Variante ist aber auch nicht besser. In dem Moment wo das 1025te
push_back kommt, werden mal eben 2048Byte Speicher dynamisch zusätzlich
zu den bereits allocierten 1024 angefordert. Danach wird umkopiert und
dann erst der Block mit den 1024Byte frei gegeben. Das dauert zwar nur
ein paar 100ns aber ob der Block zu diesem Zeitpunkt dann noch frei ist?
Der Entwickler ging ja eigentlich davon aus nur max. 1024Byte zu
brauchen. Gerade bei größeren Projekten mit einem RTOS kann das genauso
zu unerwarteten Ergebnissen führen. Auf einem PC sind diese
Betrachtungen nicht nötig, aber auf einem Controller mit begrenzten RAM
kann das kriegsentscheident sein.
temp schrieb:> Ein übliches Cortex Mx Programm hat in C++ im Debugmodus> zeitlich mit der Wirklichkeit nicht mehr viel zu tun wenn die std::lib> im Spiel ist.
Das ist ja ausgemachter Blödsinn.
Es stimmt nur, wenn der Programmierer keinen Plan hat, was er tut.
So wie du den std::vector missbrauchst, müsstest du es in C mit einem
frei allokierten Feld vergleichen, das bei jedem Durchlauf mit realloc()
um ein Element verlängert wird.
Klaus Wachtler schrieb:> So wie du den std::vector missbrauchst, müsstest du es in C mit einem> frei allokierten Feld vergleichen, das bei jedem Durchlauf mit realloc()> um ein Element verlängert.
Das ist so nicht richtig. Mit .reserve wurde der Bereich angelegt um
genau das zu vermeiden.
Klaus Wachtler schrieb:> So wie du den std::vector missbrauchst, müsstest du es in C mit einem> frei allokierten Feld vergleichen, das bei jedem Durchlauf mit realloc()> um ein Element verlängert.
Danke!
Der Vergleich von temp hinkt natürlich ohne Ende!
Mal davon abgesehn dass man die C++ Sprachfeatures auch ohne STL nutzen
kann.
Templates, echtes OOP, Überladungen usw. stehen auch ohne STL zur
Verfügung.
le x. schrieb:> Mal davon abgesehn dass man die C++ Sprachfeatures auch ohne STL nutzen> kann.> Templates, echtes OOP, Überladungen usw. stehen auch ohne STL zur> Verfügung.
Und um gleich mal dem 0815 Argument "lolol, dann kannst ja gleich C
nehmen wennst die Hälfte von C++ nicht benutzen darfst" den Wind aus den
Segeln zu nehmen:
In C hat man sich ja auch dran gewohnt nicht alle Standardfunktionen zu
benutzen. Regelmäsig wird hier ja von sprintf, sscanf usw gewarnt.
Dann sollte man fairerweise auch bei C++ akzeptieren, dass es
ressourcenintensive Funktionen gibt, auf die man aber oft verzichten
kann.
le x. schrieb:>> So wie du den std::vector missbrauchst, müsstest du es in C mit einem>> frei allokierten Feld vergleichen, das bei jedem Durchlauf mit realloc()>> um ein Element verlängert.
das war bereits widerlegt!
>> Danke!> Der Vergleich von temp hinkt natürlich ohne Ende!>
Also ich bin ja lernfähig. Wenn ich das Beispiel oben so umbaue:
1
u8Arr.resize(1024);
2
for(intn=0;n<1024;n++)
3
u8Arr[n]=n;
sehen die Verhältnisse so aus:
debug:
std::vector systicks=42184
c-array systicks=12352
release:
std::vector systicks=5413
c-array systicks=4153
> Mal davon abgesehn dass man die C++ Sprachfeatures auch ohne STL nutzen> kann.> Templates, echtes OOP, Überladungen usw. stehen auch ohne STL zur> Verfügung.
Stimmt genau. Benutze ich auch alles. Bis auf die STL. Als ich vor
24Jahren mit C++ angefangen habe gab es da noch nichts was einem
Standard entsprach. Also hat man sich für das was heute die STL abdeckt
eigenen Code geschrieben. Wenn sowas erst mal firmenweit etabliert ist,
guckt man nur hin und wieder über den Tellerrand. Wenn sich da keine
wirklich gravierenden Vorteile ergeben lohnt sich die Mühe nicht.
Moby schrieb:> Rolf Magnus schrieb:>> deshalb>> wurde im GCC die unportable Krücke mit dem ATOMIC_BLOCK eingebaut.>> Ah ja. Ein Beitrag zum Thema Portabilität der Hochsprache.
Ah ja. Manchmal ist es OOP, manchmal C++, manchmal Hochsprachen
allgemein. Ist für dich offenbar alles derselbe Topf. Du sitzt dagegen
weiter auf deinem Assembler-Teller, über dessen Rand du nicht
hinauszuschauen vermagst. Ich schrieb ja schon, daß dein angeblich so
toll passendes Beispiel auch prima dazu dienen kann, µCs insgesamt für
überflüssig zu erklären. Das zeigt ja schon, wie repräsentativ dieses
ist.
> P. M. schrieb:>> Und ein gut optimertes C-Compilat schlägt man>> von Hand in Assembler nicht so schnell.>> Entschuldigung, Unfug. Wenn man nur halbwegs gut die Möglichkeiten> "seines" Controllers nutzt und in Asm halbwegs fit ist!
Und wenn es sich um einen AVR handelt. Es gibt kaum eine andere
Architektur, die in Assembler so simpel zu programmieren ist.
> Irgendwer schrieb:>> Da könnte einem schon der Verdacht>> kommen das beim Thema Optimierung zumindest beim gcc noch einiges an>> Luft für Verbesserungen vorhanden ist.>> Schau einer an. Aber man kann ja immer noch ein paar Hundert bis Tausend> Euro in einen "ordentlichen" Compiler stecken, ich weiß schon.
Alternativ findet man sich einfach damit ab, daß das Programm nicht so
schnell wie möglich, sondern nur so schnell wie nötig läuft und damit
halt einfach etwas weniger seiner Zeit in Idle-Schleifen rumkreist. Ich
kann aus meiner Erfahrung heraus sagen, daß nur ein sehr geringer
Prozentsatz des gesamten Code wirklich so zeitkritisch ist, daß es auf
jeden einzelnen Taktzyklus ankommt, und das gilt auch für µCs.
> In der Praxis liegt der Teufel stets im Detail. Bei richtiger> Initialisierung aller Register, mindestens > halboptimaler Nutzung der> Peripherie, Interruptsystem, Event-Netzwerk, 1:1 Umsetzung der> Funktionalität und vorgesehener, schon lang (selbst) optimierter> I/O-Methoden nie und nimmer!
Weißt du das aus Erfahrung oder ist das einfach nur eine unbelegte
Behauptung? Wie groß ist der Unterschied denn in der Praxis, und wie oft
wäre der in deinen Projekten schon relevant gewesen?
> Hört doch endlich auf, den einfachen ehrlichen Programmierer mit diesem> "Zeug" an der Nase herumzuführen. Danke.
Du solltest dafür aber auch damit aufhören, deine persönliche Meinung
als allgemeingültige Fakten hinzustellen. Mich würde stark wundern, wenn
du jemals auf einem AVR in C++ programmiert hättest, und somit sind
deine Behauptungen allesamt nichtig, da sie nur auf Vorurteilen beruhen
und nicht auf Fakten.
le x. schrieb:> Moby schrieb:>> Komisch. In jedem Zitat kommt C++ vor ...>> Ja, hier hast du recht. Das ist echt komisch.> Im ganzen Thread geht es nur um plain-C, und ob man besser mittels Index> oder Zeiger ein Array kopiert.
Die gleiche Frage könnte man übrigens auch auf Basis von Assembler
stellen.
Yalu X. schrieb:> Stroustrup selbst geht da leider mit schlechtem Beispiel voran und> überlädt die Bitshift-Operatoren << und >> mit Funktionen für die> Ein-/ausgabe.
Das ist allerdings richtig. Ich habe da auch schon die Meinung gehört,
<< und >> seien in C++ die Stream-Operatoren, mit denen man halt auch
Bitshift machen kann. Eigentlich ist es aber genau anders rum.
Teilweise wird auch die Meinung vertreten, daß der Operator-Missbrauch
schon beim operator+ für Strings beginnt, da die Strings ja nicht
addiert, sondern konkateniert werden. Wer aber wirklich mal sehen will,
welchen Unfug man mit Operator-Überladung so treiben kann, sollte sich
mal boost::spirit anschauen. Siehe
http://de.wikipedia.org/wiki/Spirit_(Parser)Nachtmann schrieb:> C++ Code welcher die Features des neusten Standards nutzt ist damit> erstmal enorm schlecht wiederzuverwenden.
Als ob das bei C anders wäre. Selbst Microsoft kriegt es nicht gebacken,
C auf dem Stand von 1999 vernünftig zu unterstützen. Und gerade auch im
µC-Umfeld sieht es nicht wirklich besser aus, obwohl speziell für diesen
Bereich manche der "neueren" C-Features besonders praktisch sind.
Rolf Magnus schrieb:> Du sitzt dagegen> weiter auf deinem Assembler-Teller
... der gerade alles nötige und nichts überflüssiges zur Realisierung
klassischer, hardwarenaher 8-Bit Controllersteuerungen enthält!
Wär aber natürlich albern und für den MC-Interessierten komisch, würde
sein Interesse nicht darüber hinaus in die Hochsprache bis hin zu
'modernem' OOP gehen. Die Erkenntnisse, die man dabei für erwähntes
Einsatzgebiet gewinnen kann sind aber -wie lang und breit dargestellt-
nicht berauschend, um es mal freundlich zu formulieren. Ich habe stets
die Frage im Hinterkopf: Geht das beim angestrebten Ergebnis nicht
einfacher? Kürzer? Schneller?
Am besten wäre ja überhaupt intelligentere Controller-Hardware. Bis die
mal kommt programmiert man eben klassisch genau das was nötig ist-
natürlich und seehr richtig von Dir festgestellt, auf einem simpel
programmierbaren AVR , der für obige Zwecke, gerade in Asm, mehr als
ausreichend ist.
Rolf Magnus schrieb:> dein angeblich so> toll passendes Beispiel auch prima dazu dienen kann, µCs insgesamt für> überflüssig zu erklären.
Wenn man es mit Gewalt missverstehen will schon.
Ansonsten nimmt man ganz einfach zur Kenntnis, daß die unmittelbare
Ansprache der Hardware mit einfachen Instruktionen in jeder Hinsicht das
einfachste und beste ist.
Rolf Magnus schrieb:> Alternativ findet man sich einfach damit ab, daß das Programm nicht so> schnell wie möglich, sondern nur so schnell wie nötig läuft
... dann mal eben nur die Hardware von AVR auf ARM aufzurüsten ist ;-)
> und damit> halt einfach etwas weniger seiner Zeit in Idle-Schleifen rumkreist.
... oder weniger im energiesparenden Sleep-Mode !
Rolf Magnus schrieb:> deine persönliche Meinung> als allgemeingültige Fakten hinzustellen. Mich würde stark wundern, wenn> du jemals auf einem AVR in C++ programmiert hättest,
man muß C++ nicht beherrschen um zu erkennen, daß es für den genannten
Einsatz Krampf ist. Eine 'persönliche' Meinung ist das ja nun auch
nicht. Schaun wir mal. Wenn bald jeder C++ auf 8-Bittern einsetzt, der
große Durchbruch kommt, sehen wir weiter ;-)
> man muß C++ nicht beherrschen um zu erkennen, daß es für den genannten> Einsatz Krampf ist.
Wie willst Du Dir ohne Ahnung ein Urteil erlauben. Das ist dann
bestenfalls ein Vorurteil.
Moby schrieb:> Ich habe stets> die Frage im Hinterkopf: Geht das beim angestrebten Ergebnis nicht> einfacher? Kürzer? Schneller?
Du entscheidest dich willkürlich a priori für das Optimierungsziel
"Einfacher - Kürzer - Schneller". Es gibt auch andere Optimierungsziele:
Lesbarkeit, Flexibilität, Portierbarkeit, Modularität, usw. Ein seriöser
Programmierer wird zunächst seine Aufgabe gut durchdenken und dann
entscheiden, welche Optimierungsziele im vorliegenden Fall besonders
wichtig sind und für welche er nicht viel Effort investieren muss.
In sehr vielen Mikrocontroller-Projekten ist z.B. die Performance selbst
eines Billigst-Controllers mehr als ausreichend. Dann muss man doch um
Himmels Willen nicht die Performance optimieren, sondern achtet lieber
auf lesbaren, portierbaren Code aus flexibel auswechselbaren Modulen. In
anderen Situationen kommt es auf jeden Takt an, dann ist natürlich ein
gut vorsichtig gebautes Assembler-Programm das Mass der Dinge. Dafür
sind diese Programme meist recht überschaubar und eine
Portierung/Erweiterung sowieso gar keine Option.
Also: Wer pauschal auf Assembler und gegen C++ pocht, der hat nur eine
Sichtweise verstanden.
Moby schrieb:> Rolf Magnus schrieb:>> dein angeblich so>> toll passendes Beispiel auch prima dazu dienen kann, µCs insgesamt für>> überflüssig zu erklären.>> Wenn man es mit Gewalt missverstehen will schon.
Es ist einfach nur eine genauso unsinnige Nutzung des Beispiels wie
deine. Du versuchst hier auch nur mit Gewalt, einen Fall zu finden, in
dem C++ nix bringt. Und ich sage eben, daß für den selben Fall ein µC
sowieso nicht sinnvoll ist, egal in welcher Sprache der programmiert
ist.
Das ist, als ob du dich für die generelle Nutzung von Fahrrädern statt
Autos aussprichst, und als Beispiel die 20m-Fahrt zum Nachbarhaus
nennst. Die ist mit dem Auto ziemlich unsinnig, aber mit dem Fahrrad
auch.
> Ansonsten nimmt man ganz einfach zur Kenntnis, daß die unmittelbare> Ansprache der Hardware mit einfachen Instruktionen in jeder Hinsicht das> einfachste und beste ist.
Ebenfalls hinzunehmen ist aber, daß auch ein µC-Programm nicht
ausschließlich aus der unmittelbaren Ansprache der Hardware besteht. Ich
sehe nur zwei Fälle, in denen das anders ist: Trivialprogramme wie dein
Beispiel, die nur aus dem einen Hardwarezugriff bestehen und Programme,
bei denen man nicht sauber zwischen low-level-HW-Zugriffen und der
eigentlichen Funktion getrennt hat. Beides kommt zumindest bei mir im
Alltag nicht vor. Und genau deshalb ist dein Beispiel nicht
praxisrelevant.
> Rolf Magnus schrieb:>> deine persönliche Meinung>> als allgemeingültige Fakten hinzustellen. Mich würde stark wundern, wenn>> du jemals auf einem AVR in C++ programmiert hättest,>> man muß C++ nicht beherrschen um zu erkennen, daß es für den genannten> Einsatz Krampf ist.
Doch, genau das muß man. Es ist zwar heute weit verbreitet, daß jeder
sich für einen Experten zu allen möglichen Themen hält, auch ohne Ahnung
davon zu haben, aber das ist eben falsch.
Die Semantik von resize ist im Defaultzustand ist nunmal, dass die
Objekte ersteinmal default-konstruiert werden, wenn man keine weiteren
Parameter angibt. Somit werden die int's in diesem vector mit 0
initialisiert, wenn Du resize aufrufst. Das hat auch seinen Grund, weil
man im allgemeinen sonst keine Objekte dadrin speichern könnte.
Du kannst aber einen "NoInit-Allokator" beigeben. Dann wird sich der
Overhead auf das einmalige Setzen der Größeninformation und den
Standardkonstruktor reduzierst, weil Du die Größe nicht gleich mitgibst.
Moby schrieb:> man muß C++ nicht beherrschen um zu erkennen, daß es für den genannten> Einsatz Krampf ist.
Falsch. C++ lernt man im Gegensatz zu den meisten anderen
Programmiersprachen auch als geübter Programmierer nicht an einem
Nachmittag. Um C++ richtig einsetzen zu können, muss man die Sprache
wirklich verstehen. C++ ist nicht einfach C mit Klassen und Templates.
Es ist auch nicht Java mit Pointers. C++ ist letztlich nicht nur eine
Programmiersprache, sondern ein richtiggehendes Programmierframework. Um
zu beurteilen, wo man es einsetzen kann, sollte man es schon recht gut
beherrschen. Nur weil du zweimal an einer Flugshow warst, kannst du ja
auch nicht beurteilen, ob eine bestimmte Aufgabe mit einem Hubschrauber
zu schaffen ist.
Sehr interessant! Man kann also sagen, mindestens Klassen, Namespaces,
Inlining, Operator overloading, Konstruktoren/Destruktoren und
Referenzen erzeugen keinerlei Einbussen in der Effizienz. Templates,
wenn richtig und nicht übertrieben verwendet, ebenfalls nicht.
Überraschend finde ich den relativ hohen Overhead für die STL.
Allerdings bezieht sich das hauptsächlich auf die Code-Grösse.
P. M. schrieb:> Sehr interessant! Man kann also sagen, mindestens Klassen, Namespaces,> Inlining, Operator overloading, Konstruktoren/Destruktoren und> Referenzen erzeugen keinerlei Einbussen in der Effizienz.
Stimmt meistens, wenn man es richtig macht - aber nicht pauschal.
P. M. schrieb:> Überraschend finde ich den relativ hohen Overhead für die STL.
Ist auch nicht pauschal richtig.
Overhead wovon verglichen womit?
Overhead hat man, wenn man ein Feld fester Größe in C mit einer
dynamischen Struktur in C++ vergleicht, aber der Vergleich ist Unsinn.
Vergleicht man dagegen feste Felder in C gegen ebensolche in C++ oder
ähnlich flexible und effiziente Lösungen in beiden Sprachen,
verschwindet der Overhead auch schnell wieder.
Klaus Wachtler schrieb:> Overhead wovon verglichen womit?
Ja eben. Man muss wissen, was man will und was man braucht. Das ist wohl
letztlich der Kern der ganzen Diskussion. Die Assembler-Fraktion hier
liegt nicht falsch, wenn sie behauptet, man würde so immer noch die
kürzesten und effizientesten Programme hinkriegen. Der Fehler liegt aber
darin, dass dies meistens gar nicht die wichtigste Zielvorgabe ist.
Die Verwendung von STL-Modulen mag rechenmässig relativ teuer sein
gegenüber händisch hardgecodeten problemspezifischen Pendants. Dafür
bieten sie den Vorteil, dass man auf hohe Qualität vertrauen und
getesteten Code verwenden kann und dank der Standardisierung viel an
Lesbarkeit und Portabilität gewinnt. In den meisten Fällen überwiegt
diese Vorgabe gegenüber den Anforderungen an die Geschwindigkeit.
P. M. schrieb:> Die Assembler-Fraktion hier> liegt nicht falsch, wenn sie behauptet, man würde so immer noch die> kürzesten und effizientesten Programme hinkriegen.
Außerhalb von Trivialkram nicht einmal das. Den Compiler schlagen die in
aller Regel nicht.
P. M. schrieb:> In sehr vielen Mikrocontroller-Projekten ist z.B. die Performance selbst> eines Billigst-Controllers mehr als ausreichend.
Da rennst Du bei mir offene Türen ein ;-)
P. M. schrieb:> Es gibt auch andere Optimierungsziele:> Lesbarkeit, Flexibilität, Portierbarkeit, Modularität
... die in der Klasse klassischer 8-Bit Steuerungen allesamt auch mit
Asm Code realisierbar sind (wenn denn keine wichtigen Gründe
entgegenstehen seine Controller-Schiene zu verlassen).
P. M. schrieb:> C++ lernt man im Gegensatz zu den meisten anderen> Programmiersprachen auch als geübter Programmierer nicht an einem> Nachmittag.
Warum ist es nur so unverständlich, daß Komplexität auch ein zentrales
Argument gegen eine Programmiersprache sein kann ?
P. M. schrieb:> Wer pauschal auf Assembler und gegen C++ pocht, der hat nur eine> Sichtweise verstanden.
Nix pauschal. Ich sage nur: Bitteschön die passende Sichtweise für den
konkreten Anwendungsfall.
asdfasdf schrieb:> Wie willst Du Dir ohne Ahnung ein Urteil erlauben. Das ist dann> bestenfalls ein Vorurteil.
Etwas anderes als darauf herumzureiten, daß man sich jetzt nicht zum C++
Expertenkreis (100 Leute ;-) zählen darf bleibt ja nun nicht... Sicher
ist, den Aufwand dazuzugehören werde ich für einfache
Controllersteuerungen, die wenige Messwerte einlesen, verarbeiten,
Ausgaben machen bzw. in eine Steuerung umsetzen niemals treiben!
Moby schrieb:> asdfasdf schrieb:>> Wie willst Du Dir ohne Ahnung ein Urteil erlauben. Das ist dann>> bestenfalls ein Vorurteil.>> Etwas anderes als darauf herumzureiten, daß man sich jetzt nicht zum C++> Expertenkreis (100 Leute ;-) zählen darf bleibt ja nun nicht...
Doch: Du kannst dir auch einfach Aussagen zu Dingen, die du nicht
kennst, verkneifen.
> Sicher ist, den Aufwand dazuzugehören werde ich für einfache> Controllersteuerungen, die wenige Messwerte einlesen, verarbeiten,> Ausgaben machen bzw. in eine Steuerung umsetzen niemals treiben!
Niemand verlangt von dir, C++ zu lernen. Aber wenn du hier dazu schon
was schreibst, dann wird auch erwartet, daß du das auf Basis des
entsprechenden Wissens tust.
Rolf Magnus schrieb:> Doch: Du kannst dir auch einfach Aussagen zu Dingen, die du nicht> kennst, verkneifen.
Ich sag ja Rolf, es bleibt nichts anderes...
In der Sache selbst kann man C++ eben nicht für jeden Anwendungsfall
predigen und Du kannst davon ausgehen, daß dieser Satz hier und heute
nicht zum letzten Mal geschrieben steht ;-)
Moby schrieb:> In der Sache selbst kann man C++ eben nicht für jeden Anwendungsfall> predigen
Das tut hier niemand, außer in deiner Vorstellung.
Im Gegenteil: du bist der einzige, der hier immer seine beschränkte
Sicht allen anderen aufdrückt.
Moby schrieb:> und Du kannst davon ausgehen, daß dieser Satz hier und heute> nicht zum letzten Mal geschrieben steht ;-)
Danke für die Warnung, aber daß du von deinem bornierten Getrolle
abrückst, hofft eh keiner mehr.
Danke dafür, daß du einen Thread, der zumindest für anderemal
interessant war, platt quasselst.
Moby schrieb:> P. M. schrieb:>> Wer pauschal auf Assembler und gegen C++ pocht, der hat nur eine>> Sichtweise verstanden.>> Nix pauschal. Ich sage nur: Bitteschön die passende Sichtweise für den> konkreten Anwendungsfall.
Eigentlich behauptest du ziemlich offensiv, dass C++ auf 8-Bittern Fehl
am Platz ist. Von Betrachtung des "konkreten Anwendungsfalls" kann bei
dir keine Rede sein. Von Betrachtung verschiedener Prioritäten in einem
Softwareprojekt schon gar nicht. Für dich ist völlig klar, dass auf
einem 8-Bitter die Recheneffizienz das Mass aller Dinge ist. Aspekte wie
Lesbarkeit, Portierbarkeit, Flexibilität, Modularisierung usw. zählen
für dich nicht.
Klaus Wachtler schrieb:> du bist der einzige
versuchen zu isolieren,
> der hier immer seine beschränkte Sicht> deinem bornierten Getrolle
vesuchen zu disqualifizieren,
> der zumindest für anderemal> interessant war, platt quasselst.
versuchen festzulegen was 'interessant zu sein hat'
Klaus Wachtler schrieb:> Ja gut, einen Dildo kann man leicht in ASM programmieren :-)
versuchen lächerlich zu machen
... sind nun mal alles keine recht überzeugenden Antworten, lieber
Klaus. Aber ich verstehe, daß sonst nichts anderes bleibt, die geradezu
ideologische C++ Anwendung hier mit herablassendem Experten-Gestus
durchzudrücken.
P. M. schrieb:> Es gilt übrigens> als sehr unfreundlich, ein Posting Satz für Satz zu zitieren und zu> kontern.
Quatsch. Das behaupten nur so Typen wie du.
Es ist die einzige Möglichkeit, eine sinnvolle Diskussion zu führen.
P. M. schrieb:> Eigentlich behauptest du ziemlich offensiv, dass C++ auf 8-Bittern Fehl> am Platz ist. Von Betrachtung des "konkreten Anwendungsfalls" kann bei> dir keine Rede sein.
Der konkrete Anwendungsfall ist die klassischen 8-Bit
Controllersteuerungen, die
> wenige Messwerte einlesen, verarbeiten,> Ausgaben machen bzw. in eine Steuerung umsetzen
Möglicherweise wird das ja erst durch tausendfache Wiederholung zur
Kenntnis genommen ;-)
P. M. schrieb:> Für dich ist völlig klar, dass auf> einem 8-Bitter die Recheneffizienz das Mass aller Dinge ist.
Für mich ist völlig klar, daß Maß aller Dinge die Minimierung des
Aufwands für eine gegebene Anwendung ist. Die Minimierung von Rechenzeit
und Platzbedarf tragen dazu bei, indem sie die Hardware-Anforderungen
minimieren.
> Aspekte wie> Lesbarkeit, Portierbarkeit, Flexibilität, Modularisierung usw. zählen> für dich nicht.
Wer sagt das? Wo steht das? Ich sagte, auch in Asm ist das möglich wenn
man auf seiner Controller-Schiene bleiben kann. Zu letzterem tragen
wiederum die Minimierung der Hardware-Anforderungen bei. So schließt
sich ein Kreis, ein Gesamtkonzept, das aufgeht wenn alle Teile
zueinander passen.
Ich hatte Dir im letzten Beitrag aber auch eine Frage gestellt.
Warum möchtest Du sie nicht beantworten?
Das Thema hier ist aber wie man es in C++ machen kan und nicht welche
Gründe es gibt, es zu lassen. Ich mische mich auch nicht ein, wenn ASM-,
BASCOM-, Luna-, etc. Freunde ihre Probleme wälzen. Danke für dein
hoffentlich zu findendes Verständnis.
ach.. wo sind wir denn jetzt gelandet?
P. M. schrieb:> Ein seriöser> Programmierer wird zunächst seine Aufgabe gut durchdenken und dann> entscheiden, welche..
Es ist immer wieder ärgerlich, derartige Prämissen als Argumente lesen
zu müssen.
Man schaue sich nur mal in diesem Forum um: Da gibt es haufenweise
Beiträge, wo Leute, die sich selbst für Programmierer halten, ihre
Vorhaben überhaupt nicht gut durchdenken, sondern ihre Ideen im
Geradausgalopp erschlagen wollen.
Beispiele? Aber ja doch:
LED0.ON = Key1.Pressed;
So ähnlich konnte man es jüngst hier lesen - als Ziel für die Verwendung
von C++. Ich wage die Behauptung, daß es sich bei solchen Programmierern
um mindestens die Hälfte aller Programmierer handelt. "Ein seriöser
Programmierer wird.." - nein, dies ist lediglich hehres Wunschdenken und
NICHT Realität.
Aber kommen wir direkt zu C++ zurück:
Könnte mir mal jemand am konkreten Beispiel dieses Threades erklären,
was man denn mit den über C hinausreichenden Mitteln von C++ z.B.
innerhalb eines geräteseitigen VCP-Treibers für den USB-Core eines µC,
oder für das Benutzen des TimerTicks oder für das Handling des SDIO
Cores oder der diversen Counter/Timer denn besser als mit purem C
erledigen kann?
Ich meine wirklich BESSER_ und nicht _FORMALISTISCHER.
Moby schrieb:> Warum ist es nur so unverständlich, daß Komplexität auch ein zentrales> Argument gegen eine Programmiersprache sein kann ?
Darauf gibt es eine sehr einfache Antwort: Weil die Einsicht nicht zum
Selbstverständnis paßt.
Leute, die irgend eine Programmiersprache endlich erlernt haben (je
schwieriger desto besser), sind stolz darauf und sehen mit innerer
Geringschätzung auf den Rest der Welt.
Sie gehören endlich dazu! - also zum Kreis der Erleuchteten (resp.
haben endlich den erhofften Stallgeruch) - und wenn jemand ihnen sagt,
daß er genau DIESE Programmiersprache für schlecht weil zu komplex hält,
dann übersetzt das Selbstverständnis eines solchen Menschen das in "der
ist ein Außenseiter und bloß zu doof". Man schaue z.B. mal in den
FPGA/VHDL-Bereich. Der strotzt von solchen Beispielen. Aber auch in
genau DIESEM Thread kann man das auch x-mal lesen: "Bevor du nicht C++
Guru bist, ignoriere ich deine Sicht der Dinge". Genau DAS ist die
Scheuklappe.
W.S.
Gerne hätte auch jemand erklärt, in welchem konkreten Fall "richtiges"
C++, also jenes, das irgendwelche "nicht C" Features benutzt, auf MCs
Vorteile bringt. Nur leider sind potentielle Autoren ob dem massiven
"geht nicht" Geschreis einiger weniger verschreckt worden. Oder habe
schlicht besseres zu tun als sich anpöbeln zu lassen. Schade! Wäre
sicher interessant geworden.
Bastler schrieb:> schlicht besseres zu tun als sich anpöbeln zu lassen
Anpöbeln nenn ich sowas:
Masl schrieb:> Never discuss with an Idiot...
An meine Adresse wohlgemerkt.
Jemand der tatsächlich den Vorteil von C++ allgemeingültig für
hardwarenahen Zugriff am einfachen Beispiel vorzutragen weiß wird sich
kaum abschrecken lassen. Allein, auf den warte ich hier immer noch ;-(
Moby schrieb:> P. M. schrieb:>> Für dich ist völlig klar, dass auf>> einem 8-Bitter die Recheneffizienz das Mass aller Dinge ist.>> Für mich ist völlig klar, daß Maß aller Dinge die Minimierung des> Aufwands für eine gegebene Anwendung ist. Die Minimierung von Rechenzeit> und Platzbedarf tragen dazu bei, indem sie die Hardware-Anforderungen> minimieren.
Uu setzt die Prämisse, dass die Minimierung von Rechenzeit und
Platzbedarf immer eine wichtige Zielvorgabe ist. Aber das ist falsch.
So lange man nicht gerade dämlich-verschwenderisch mit den Resourcen
umgeht - und das tut C++ nicht - ist der Rechenaufwand oft völlig egal.
Gerade bei "klassischen 8-Bit-Steuerungen" ist das oft der Fall. Wenn
ich zwei, drei Sensoren auslesen muss, zwei, drei Relais schalten,
zweimal PWM habe, ein paar Taster und ein Display ansteuern muss und das
ganze im Sekundentakt passieren kann, dann habe ich selbst auf einem
kleinen AVR endlos Leistungsreserven. Da ist mir viel wichtiger, eine
Abstraktion zu haben, welche das Zusammenspiel der vielen Komponenten
flexibel, modular und lesbar abbildet. Und das geht nunmal mit einer
höheren Programmiersprache viel besser als in Assembler.
Wie gesagt: Die Kritik an deiner Haltung ist, dass du nicht anerkennen
kannst, dass es sehr viele Situationen gibt, wo man gerne etwas
Rechenpower zugunsten von Lesbarkeit, Modularität, Flexibilität,
Portierung usw. verschenkt.
Moby schrieb:> Jemand der tatsächlich den Vorteil von C++ allgemeingültig für> hardwarenahen Zugriff am einfachen Beispiel vorzutragen weiß wird sich> kaum abschrecken lassen. Allein, auf den warte ich hier immer noch ;-(
Es gab mehrere Beispiele, wie man in C++ etwas low-level implementieren
kann und danach über eine praktische Abstraktion ansprechen. Du hingegen
konntest bislang kein Beispiel oberhalb eines Trivialfalles zeigen, wo
man mit Assembler glücklicher wird als mit C/C++.
Bastler schrieb:> Nur leider sind potentielle Autoren ob dem massiven> "geht nicht" Geschreis einiger weniger verschreckt worden.
Das sehe ich nicht so. Hättest du nicht geschrieben "geht nicht",
sondern "macht keinen Sinn", dann könnte ich dir zustimmen.
Also, mal ganz simpel: Das, was über einfaches C bei C++ hinausgeht,
besteht im Wesentlichen aus der objektorientierten Erweiterung von C.
Ja, es ist noch ein bissel anderes in der Büchse, aber das lassen wir
erstmal. Hier wurde argumentiert, daß es für die Lesbarkeit vorteilhaft
sei, Hardware zunächst in zugehörige Objekte zu verwandeln oder
einzuwickeln (man nenne es wie man will), um es danach (zitat) "und
danach über eine praktische Abstraktion ansprechen" eben
objektorientiert ansprechen zu können.
Angeblich sei dies besser lesbar oder programmtechnisch vorteilhaft.
Das zweifle ich hier mal ganz massiv an. Ob man beispielsweise schreibt
PORT4CLR = (1<<Relais1);
oder
Relais1.State = 0;
ist wirklich Geschmackssache. Der Unterschied ist, daß in ersterem Falle
die Sache mit nur einem direkten Befehl erledigt ist, im zweiten Falle
aber ganz anders funktioniert: Dort muß es ein Objekt Relais1 geben,
dieses Objekt muß Eigenschaften haben und diese Eigenschaften müssen
mittels der Methoden des Objektes geändert werden. Es braucht daher im
zweiten Falle immer eines Methodenaufrufes des Objektes und das ist
tatsächlich aufwendiger, als die Sache direkt zu erledigen. Also 1:0 für
plain C. Aber es geht weiter: Objekte existieren nicht per se, sie
müssen als Instanziierungen von Klassen bzw. Objekttypen erstmal
hervorgebracht werden und das bedeutet, sie müssen per Konstruktor
erzeugt werden, was zuinnerst wieder ein Unterprogrammaufruf ist - und
wenn man keine Möglichkeit hat, so etwas zur Übersetzungszeit
vollständig erledigt zu kriegen, dann ist dafür niccht nur Laufzeit und
Programmspeicher nötig, sondern auch RAM, in welchem die Instanz
aufgebaut wird.
Ist so etwas angemessen? Nein. Die Hardware in einem µC ist vorhanden.
Sie muß zwar eingerichtet werden, aber sie ist eben nur EINMAL
vorhanden. Der Sinn von Klassen und Objekt-instanziierungen ist
hingegen, daß man mit einem einzigen Modell eine Vielzahl von
gleichartigen Objekten gleichen Verhaltens erzeugen kann - und das ist
nur für reine Softwaredinge sinnvoll, nicht hingegen für Hardware. Die
ist gegeben. Ein sinnvolles Beispiel wären z.B. Punkte auf einem
Display: Sowas kann dutzende Male auftreten, die Eigenschaften können
von winzig bis groß oder von rot bis lila gehen und die Methoden vom
SichZeichnen bis zum Farbändern oder Position ändern usw. gehen. Dafür
sind objektorientierte Ansätze gut. Aber eben NICHT für den einen
Treiber, der die serielle Schnittstelle bedient.
W.S.
Moby schrieb:> Anpöbeln nenn ich sowas:>> Masl schrieb:>> Never discuss with an Idiot...
Aber Moby, das Thema hatten wir beide doch auch schon mal.
Wer vollkommen unzugänglich für jede Art der Kommunikation ist und als
einzige Reaktion auf wirklich jedes Argument seine eigenen Ansichten
wiederholt, der ist im klinischen Sinne betrachtet, ja, etwas platt
ausgedrückt, ein Idiot.
Im dem Sinne als das diese arme Kreatur unfähig ist noch den Input
seiner Umwelt aufzunehmen UND zu verarbeiten.
Die Reaktionen lassen zwar noch auf einen Verarbeitungsprozess
schliessen, aber das wahnhafte überwiegt und reisst alles an sich.
Zum Leidwesen ihrer Umwelt sind diese armen Wesen dann oft sehr
mitteilungsbedürftig und wollen auf biegen und brechen auch andere von
Ihrem Wahn überzeugen.
Das Internet hat da für beide Seiten einen großen Vorteil.
Wir können Dich einfach ausblenden, auch wenn das nicht immer leicht ist
und müssen nicht befürchten das Du uns plötzlich anfällst und die Kehle
durchbeisst.
Du hast ein Publikum, was Dir ganz offensichtlich viel bedeutet, und
kannst Deine Thesen verbreiten ohne Dir ständig über die Schulter
schauen zu müssen ob die Männer in weiss um die Ecke kommen.
In dem Sinne sei nicht gekränkt wenn man Dich Idiot nennt.
Du tust ja im Endeffekt nichts anderes mit den Menschen die andere
Meinungen und Erfahrungen vertreten.
Ich persönlich finde Dich recht unterhaltsam.
Wenigstens kannst Du einigermassen fomulieren, wenn sich der Inhalt auch
nie ändert. Das ist mehr als manch anderer hier zustande bringt.
Je kruder Deine Ansichten umso verklausulierter Deine Texte, aber auch
das ist nichts unbekanntes bei wahnhaften Persönlichkeiten.
Weiter so, auch wenns manchmal wehtut.
Stimmt! Die Ports B, C, D (oder auch A..G) sind nur einmal vorhanden,
genau wie Uart0 und Uart1 und die Timer sind ja auch einzeln mehrere.
Die erwähnte Vielzahl beginnt bei der Zahl Zwei. Und die Templates, um
die es hier eigentlich geht, sind sowas wie der C-Preprozessor, nur
typ-sicher und mit viel mehr Möglichkeiten. Und Klasses ohne Instanz
gehen gar nicht, also wird's fett. Zumindest falls man keine Vorstellung
hat, was auch angeblich so schlechte Compiler wie GCC daraus machen. Der
wird ja gerade per Zitat von Linus "gedisst", in dem dieser einen Bug im
x86-64 Backend als hernimmt, um sich auszukotzen.
Bastler schrieb:> Die Ports B, C, D (oder auch A..G) sind nur einmal vorhanden
Richtig. Jeder Port ist nur einmal vorhanden - und die Ports
unterscheiden sich fast IMMER massiv voneinander, insbesondere in dem,
was grad implementiert ist, welche Bits gerade vorhanden sind,
anderweitig belegt sind und so weiter. Schau mal in so ein
Hardware-Manual zu einem konkreten µC, da wirst du es sehen können. Es
heißt zwar "PortX,Y,Z" aber es sind überhaupt nicht gleiche Objekte.
W.S.
W.S. schrieb:> Angeblich sei dies besser lesbar oder programmtechnisch vorteilhaft.>> Das zweifle ich hier mal ganz massiv an. Ob man beispielsweise schreibt> PORT4CLR = (1<<Relais1);>> oder> Relais1.State = 0;
Der Unterschied ist (bzw. könnte sein):
PORT3CLR = (1 << Relais1); // gültig, aber falsch
Relais1.State = 0; // das tut was man sich darunter vorstellt.
C++ kann einfach helfen exakt solche Fehler zu vermeiden. Natürlich kann
man das auch in C machen, keine Frage.
W.S. schrieb:> aber es sind überhaupt nicht gleiche Objekte.
Nein, aber sie sind ähnlich. Vermutlich wird jedes der 87 GPIO Pins grob
etwas können wie: Input, Output, Pull-Up, Pull-Down… Das manche dann
noch andere Dinge können, steht auf einem anderen Blatt – Aber: genau
das kann OOP verhältnismäßig gut. Ein interrupt fähiger Pin ist halt
immer noch ein GPIO Pin. Und ein UART ist halt erstmal ein UART – mir
doch egal, was da drunter hängt. Ob das nun eine USB Seriell CDC ist
oder eine RS232 Schnittstelle oder ein RS485 Wandler ist mir oft egal.
Sprich die Objekte müssen nicht gleich sein. Sie müssen sich nur
entsprechend eines Aspektes gleich verhalten.
Moby schrieb:> wenige Messwerte einlesen, verarbeiten,> Ausgaben machen bzw. in eine Steuerung umsetzen
Sieh dir mal eine typische Anwendung für einen 8bitter (ATMega169) an.
z.B. Heizungsregler HR20. Temperatursensor, Stromsensor, Drehgeber, ein
paar Tasten und eine Lichtschranke sowie das Display. Da gibt's auch
eine OpenSource Alternativsoftware dafür.
http://openhr20.sourceforge.net Und jetzt möchte ich wirklich mal wissen
ob es auf der ganzen Welt noch einen einzigen Idioten gibt der sowas in
Assembler macht.
@Moby:
Falls du sowas in lesbarem Assembler gebacken kriegst, nehme ich den
Idioten zurück und behaupte das Gegenteil.
temp schrieb:> Moby schrieb:>> wenige Messwerte einlesen, verarbeiten,>> Ausgaben machen bzw. in eine Steuerung umsetzen>> Sieh dir mal eine typische Anwendung für einen 8bitter (ATMega169) an.> z.B. Heizungsregler HR20. Temperatursensor, Stromsensor, Drehgeber, ein> paar Tasten und eine Lichtschranke sowie das Display. Da gibt's auch> eine OpenSource Alternativsoftware dafür.> http://openhr20.sourceforge.net Und jetzt möchte ich wirklich mal wissen> ob es auf der ganzen Welt noch einen einzigen Idioten gibt der sowas in> Assembler macht.
Offensichtlich hat Moby noch nicht viel gemacht in der Richtung. Ist
zwar kein C++, sondern C, aber ein weiteres Beispiel, dass man so leicht
nicht in Assembler hätte hinkriegen können habe ich auch noch:
https://github.com/emsec/ChameleonMini/tree/master/Firmware/Chameleon-Mini
P. M. schrieb:> So lange man nicht gerade dämlich-verschwenderisch mit den Resourcen> umgeht - und das tut C++ nicht - ist der Rechenaufwand oft völlig egal.> Gerade bei "klassischen 8-Bit-Steuerungen" ist das oft der Fall.
WENN die Kapazitäten des verwendeten (und nicht speziell für viel Code
ausgesuchten) Controllers das hergeben, wenn das Energiebudget keine
Rolle spielt, wenn die entsprechende Entwicklungsumgebung parat steht-
und der ausgebildete und motivierte C++ Entwickler davor,
...hast Du immer noch nicht die Frage beantwortet, warum es zur
Programmierung einfacher 8-Bit Steuerungen gegenüber der 1:1
Funktion-codierenden Asm/C Programmierung zwingend von Vorteil ist,
P. M. schrieb:> eine> Abstraktion zu haben, welche das Zusammenspiel der vielen Komponenten> flexibel, modular und lesbar abbildet.
Zur Beantwortung meiner anderen Frage bist Du wohl auch nicht in der
Lage, aber ich kann mir vorstellen warum ,-)
P. M. schrieb:> Die Kritik an deiner Haltung ist, dass du nicht anerkennen> kannst, dass es sehr viele Situationen gibt, wo man gerne etwas> Rechenpower zugunsten von Lesbarkeit, Modularität, Flexibilität,> Portierung usw. verschenkt.
Die mag es geben. Das habe ich für komplexere, ggf.
controllerhardware-übergreifende Projekte nicht abgestritten.
P. M. schrieb:> konntest bislang kein Beispiel oberhalb eines Trivialfalles zeigen, wo> man mit Assembler glücklicher wird
Der Trivialfall steht für eine unüberschaubare Anzahl von Fällen.
Ob ich 1 oder 100 Eingänge abfrage, 1 oder 100 Ausgänge schalte, 1 oder
100 Messwerte auslese und verarbeite oder viele serielle Verbindungen
unterhalte- das hardwarenahe Prinzip der simplen direkten
Registeransprache bleibt dasselbe. Stehen alle Routinen zur Verfügung
(passend selbst-erstellt und nicht von irgend einem Compiler geschenkt)
ist die Programmierung der Abläufe in Asm einfach.
Michael Knoelke schrieb:> ...
Aber Michael, wenn Du so unerhört viel Mühe aufwendest, für soviel
kunstvoll verpackte Unterstellungen und Beleidigungen fern jeder
fachlichen Aussage zum Thema, dann muß der Frust wirklich tief sitzen.
Lässt tief blicken. Donnerwetter.
apr schrieb:> C++ kann einfach helfen exakt solche Fehler zu vermeiden.
... die sich ja nur aus den vielerlei hochsprachigen Schreibweisen und
Ausdrucksmöglichkeiten ergeben. Sbi PORTA,0 und gut ist- aber warum
einfach wenns auch kompliziert geht?
temp schrieb:> nehme ich den> Idioten zurück
Der ist mir herzlich wurscht.
Aber so einen Heizungsregler mit ein paar der genannten Komponenten hab
ich z.B. auch in Betrieb, natürlich in Asm programmiert ;-)
apr schrieb:>> Der Unterschied ist (bzw. könnte sein):> PORT3CLR = (1 << Relais1); // gültig, aber falsch>> Relais1.State = 0; // das tut was man sich darunter vorstellt.>> C++ kann einfach helfen exakt solche Fehler zu vermeiden. Natürlich kann> man das auch in C machen, keine Frage.>
Sorry, wieso "gültig, aber falsch" und wieso "das tut was man sich
darunter vorstellt"? Ich verstehe nicht, wie man das ohne weitere
Hintergrundinformationen (Schaltplan und MikroController Typ) bewerten
kann. Oder muss man hier mehr das
>"(bzw. könnte sein)"
betonen? Aber dann ist der Beitrag doch ziemlich "dünn".
Ob was tut oder nicht, steht für die einem
a) im Schaltplan,
b) in der Spezifikation des Mikro-Controller
c) in der Spezifikation der Programmiersprachen
d) und in der Spezifikation der API
und für die anderen im Tutorial Ihrer Plattform.
Wenn die einen keinen Fehler gemacht haben, ist es auch "nicht falsch",
und wenn die Plattform nicht genügend gut getestet ist, tut das andere
auch nicht was man sich darunter vorstellt.
Aber das hat nicht mit C / C++ zu tun.
Moby schrieb:> ... die sich ja nur aus den vielerlei hochsprachigen Schreibweisen und> Ausdrucksmöglichkeiten ergeben. Sbi PORTA,0 und gut ist- aber warum> einfach wenns auch kompliziert geht?
Nein, die ergeben sich aus dem Problem, dass man zwei anstatt einem
Namen übergeben muss.
Achim K. schrieb:> Sorry, wieso "gültig, aber falsch" und wieso "das tut was man sich> darunter vorstellt"? Ich verstehe nicht, wie man das ohne weitere> Hintergrundinformationen (Schaltplan und MikroController Typ) bewerten> kann. Oder muss man hier mehr das>>"(bzw. könnte sein)"> betonen? Aber dann ist der Beitrag doch ziemlich "dünn".
Genauso wie alle anderen hier ;)
Es ging mir schlicht darum: Damit so eine typische Bitspielerei das tut
was man dachte dass es tut, muss in dem Konstrukt:
PORT_DEFINITION |= 1 << PIN_NUMMER
beide zusammenpassen. Tun sie das nicht passieren im Zweifelsfall Dinge
und es ist ein Fehler der leicht zu übersehen ist. Während dagegen ein:
motor.run_forward(); gegen ein bomb.explode() irgendwie für mich als
Mensch leichter unterscheitbar ist. Während sbi PORTA,0 oder sbi PORTB,0
schnell mal übersehen wird. Und auch ein sbi MOTOR_PORT,MOTOR_PIN ist
leichter mit sbi BOMB_PORT,MOTOR_PIN verwechselt.
Mein "(könnte sein)" sollte einfach nur Bedeuten, dass ich z.B. mit C++
dafür sorgen kann, dass ein Relais_Pin keinem LED Pin zugewiesen werden
kann – nicht mehr und nicht weniger.
>> Ob was tut oder nicht, steht für die einem> a) im Schaltplan,> b) in der Spezifikation des Mikro-Controller> c) in der Spezifikation der Programmiersprachen> d) und in der Spezifikation der API> und für die anderen im Tutorial Ihrer Plattform.
Klar. Aber es ist unwahrscheinlich, dass Port3 und Port4 einfach
parallel geschalten sind. Deswegen meinte ich es, sei ein Fehler. Ich
hoffe du kannst mir diese freie Interpretation des Beispieles verzeihen.
>> Wenn die einen keinen Fehler gemacht haben, ist es auch "nicht falsch",> und wenn die Plattform nicht genügend gut getestet ist, tut das andere> auch nicht was man sich darunter vorstellt.>> Aber das hat nicht mit C / C++ zu tun.
apr schrieb:> Klar. Aber es ist unwahrscheinlich, dass Port3 und Port4 einfach> parallel geschalten sind. Deswegen meinte ich es, sei ein Fehler. Ich> hoffe du kannst mir diese freie Interpretation des Beispieles verzeihen.>
OK, jetzt verstehe ich was Du meintest.
Mit den sprechenden symbolischen Namen hast Du natürlich recht, die
Vereinfachen das Verstehen von Programmen (wie mein Beitrag oben
ungewollt ja auch gezeigt hat :-) ).
Hallo,
ein paar Punkte hat Rainer Grimm auf der Meeting C++ 2013 mit Fokus auf
C++11 zusammengefasst.
Ein Buch, dass sich mit dem Thema beschäftig kenne ich leider nicht, ich
denke aber man kommt recht weit, wenn man einfach mal überlegt, wie das
eine oder andere C++ feature implementiert ist. Daraus kann man dann
ableiten welchen Ressourcenbedarf das feature hat. strikte Typisierung,
namespaces haben z.B. überhaupt keine Laufzeitkosten, RTTI, dynamic
memory allocation und exceptions haben sehr hohe Laufzeitkosten.
Notfalls mal die Annahmen anhand des map files oder compiler genierten
assemblers überprüfen.
mfg Torsten