selbst wenn der speicher voll sein sollte, das programm kann man noch
sehr stark optimieren und bestimmt noch mehrere kb einsparen.
Wie genau das sollte dir vielleicht selbst bei den case sprüngen
sichtbar sein, warum schreibst du jedes mal die ganzen zeilen wie
display löschen usw... das reicht doch einmal und nur die beiden zeilen
text sind jedes mal anders das reicht doch wenn du das in den case
bereich schreibst.
Da du nicht den gesamten Quellcode zeigst (mir fehlen da sämtliche
Includes usw.) ist das schwer zu sagen. So oder so ist der Quellcode
aber extrem ineffizient.
brauchen doppelt Platz. Einmal für den String "Fehler" im Flash, einmal
für eine komplett unnötige Kopie desselben Strings im eh schon knappen
RAM!
=> PSTR, pgmspace.h, ...
und, wie ist "AbsDelay" definiert?
hoffentlich als Variante von
Das Problem ist, dass das mein erstes größeres Projekt ist. Ich habe bis
jetzt nur Lauflichter, Uhren, kleinere Steuerungen, etc... programmiert.
Und dies habe ich immer zum Laufen gebracht.(Wahrscheinlich halt auch
mit jede Menge zu vielem Code)
Das mit dem LCD löschen ist klar, habe ich jetzt ganz nach oben gesetzt.
Text "Fehler" kann ich ja in ein Unterprogramm packen und dann aufrufen.
Oder gibt es da eine bessere Lösung?
kraemer90 schrieb:> Oder gibt es da eine bessere Lösung?
Ja, indem du den Text im Programmspeicher ablegst; siehe dazu die
entsprechenden Abschnitte im AVR-GCC-Tutorial
Leg dir deine Fehlermeldungen als konstanten String im Flash ab, am
besten sogar als Array.
Dann greifst du mit dem Fehlerindex auf diese Array zu und holst dir den
auszugebenden Text.
Damit sparst du dir die ganze switch-Konstruktion.
:-)
Ein weiteres Problem ist auch dass ich C Control von Conrad habe, da
gehen die speziellen Befehle nicht.
"Deklarationen von Variablen im Flash-Speicher werden durch das
"Attribut" PROGMEM ergänzt."
PROGMEM funktioniert bei mir aber nicht, der Compiler bringt folgende
Fehlermeldung:
Syntax Fehler - unerwartetes Symbol: 'PROGMEM'
ein Fehler - Kompilation abgebrochen.
kraemer90 schrieb:> PROGMEM funktioniert bei mir aber nicht, der Compiler bringt folgende> Fehlermeldung:>> Syntax Fehler - unerwartetes Symbol: 'PROGMEM'> ein Fehler - Kompilation abgebrochen.
Ja was für einen Compiler, der Deutsche Fehlermeldungen ausgibt, hast du
denn?
kraemer90 schrieb:> C-Control-Pro IDE, bei anderen läuft ja der C-Control-Controller nicht
Achso, (fast) alles hier verwendet GCC, keine Ahnung wie man das der
komischen C-Control-IDE beibringt. Afaik basieren die neueren C-Controls
auf AVRs, also sollte einer Verwendung von anderen / besseren :>
Compilern nichts im Wege stehen.
Ja, habe ich auch schon gemerkt, aber laut Recherchen hier im Forum
bekommt man das Programm nur mit dem C Control PRO IDE auf den
Controller übertragen. Und einfach ein Hex-File einlesen geht auch
nicht.
kraemer90 schrieb:> !Gast schrieb:>> kraemer90 schrieb:>>>char fehler PROGMEM = "Fehler";>> Das ist in der Tat ein Fehler... char fehler[] = "Fehler";>>>
1
charfehler[]="Fehler";
>> Syntax Fehler - unerwartetes Symbol: '[]'> ein Fehler - Kompilation abgebrochen.
Dann ist die benutzte Sprache nicht C.
kraemer90 schrieb:> Darüber gibt es keine Informationen. Welcher Controller unter der
Hmm.. das Ding heißt Mega32, da könnte doch ein .... ATmega32
drunterstecken...
Mein Rat: Wenn du's ernst meinst, Vergiss' C-Control
Das muss ich dann erstmal mit meinem Beauftragten abklären, ist nämlich
ein Projekt für den Betrieb (Ich bin auch noch Azubi). Für kleinere
Sachen ist es ja auch recht einfach, man hat in kürzester Zeit etwas am
laufen. Für komplexere Dinge ist aber gleich Schluss...
Im C-Control Mega32 ist ein ATmega32 drin, im Mega128 ein ATmega128.
Das Entwicklungssystem ist kein Compiler im herkömmlichen Sinn.
Auf dem ATmega läuft ein Tokeninterpreter, der CompactC-Quellcode wird
in Tokens übersetzt (so ähnlich wie Java) und auf einer virtuellen
Maschine am ATmega ausgeführt.
Text = "Verbindung"; //auszugebender Text
"Verbindung" liegt automatisch nur im Flash, das PROGMEM Attribut wird
hier nicht benötigt.
Und Text ist ja nur einmal definiert, es wird also auch nicht besonders
viel RAM verschwendet.
Allerdings sollte man sich schon überlegen, ähnliche Textausgaben so
aufzuteilen, dass gleich lautende Texte in Funktionen gruppiert werden.
Eben genau so, aber mit allem, das öfter vorkommt:
1
voidfehler(void)
2
{
3
LCD_Locate_Ext(1,1);//Zeile 1, Pos 1
4
Text="Fehler";//auszugebender Text
5
LCD_Write_Text_Ext();//Text schreiben
6
}
Dann dürfte das Speicherproblem schon gelöst sein.
Grüße,
Peter
> Allerdings sollte man sich schon überlegen, ähnliche Textausgaben so> aufzuteilen, dass gleich lautende Texte in Funktionen gruppiert werden.>> Dann dürfte das Speicherproblem schon gelöst sein.>> Grüße,>> Peter
Ich werde jetzt erstmal alles was mehrmals vorkommt in Unterprogramme
gruppieren und dann mal weiter programmieren.
Gibt es einen mathematisch ausdrückbaren Zusammenhang zwischen F/F1 und
BUn-o - KLp-q ?
Peter schrieb:> char* Texte[]
Doch an ebendem scheitert die minderbemittelte C-Control IDE :(
Peter schrieb:> char* Texte[] = {"BU2-8 - BU1-4", "BU2-8 - BU1-1", "BU2-8 - BU1-3", "BU2-8 -
BU1-2", "BU2-8 - BU1-3", "BU2-8 - BU1-2", "BU2-8 - KL1-1","BU2-8 - KL1-2"};
> verbindung();> Text = Texte[F1];
Da wärs noch perfekt, wenn du die Texte im Flash abspeichern könntest.
Aber das musst du im Handbuch für CompactC nachschauen, ob das geht.
:-)
[c]
char* Texte= {"BU2-8 - BU1-4\0BU2-8 - BU1-1\0BU2-8 - BU1-3\0BU2-8 -
BU1-2\0BU2-8 - BU1-3\0BU2-8 - BU1-2\0BU2-8 - KL1-1\0BU2-8 - KL1-2"};
Text = Texte[F1*13];
so sollte auch auch gehen, ist aber nicht sehr sauber.
Da geht noch viel mehr.
Es besteht ein Zusammenhang zwischen der Zahl hier
Text = "BU2-8 - BU1-4"
^
|
und dem Parameter F. Diesen Teil des Strings kann man daher per sprintf
leicht generieren und damit fällt der komplette switch über F raus. Die
ganze Funktion kann in weniger als 40 Zeilen forumliert werden.
Der ganze Originalcode ist ein Musterbeispiel dafür, wie man durch
Ausschalten der kleinen grauen Zellen Code unnötig aufblähen kann. Das
ganze hat Ähnlichkeit mit einer Multiplikation, die der Programmierer so
gelöst hat, indem er das kleine 1*1 in Form von 10 cases mit jeweils 10
Subcases implementiert. Mit Einsatz der kleinen grauen Zellen hätte er
stattdessen ganz einfach eine Multiplikation geschrieben.
Und wenn man sich ein paar besser geeignete LCD Funktionen macht, dann
könnte man auch diesen Code noch weiter abspecken und übersichtlicher
machen.
Das könnte dann so aussehen
Florian K. schrieb:> Na toll, man kann gar keine Text-Arrays anlegen>> "Semantik Fehler - String Initialisierungseinträge werden momentan nicht> unterstützt"
Besorg dir einen ordentlichen Compiler.
Es gibt nichts schlimmeres als wie wenn man mit untauglichem Werkzeug
arbeiten muss.
sprintf ist an dem Quelltext von Karl heinz Buchegger das Einzige, was
die C-Control nicht kann.
Nachdem hier aber keine großartige Formatierung passiert, kann man das
leicht durch eine eigene Funktion ersetzen.
Das hier zum Beispiel:
1
sprintf(Buffer,"Pruefschritt %d",F);
F liegt im Bereich zwischen 1 und 8, wenn ich das richtig sehe. Somit
ist die Zahl einstellig.
Damit kann man das ASCII-Zeichen, das an letzter Stelle in Text steht,
ausrechnen und dort einsetzen:
1
Text="Pruefschritt ";
2
Text[13]=F+'0';
3
LCD_Write_Text_Ext();
Für das zweite sprintf geht das entsprechend genauso.
>Besorg dir einen ordentlichen Compiler.
Dem kann ich mich nur anschließen. Wenn es in deinem Projekt irgendwie
möglich ist.
Hier gibt es ein Programm, das Hexfiles von anderen Compilern auf die
unveränderte C-Control laden kann:
Beitrag "Programmvorstellung "CCPro-Loader" - natives C (ohne Interpreter) auf der C-Control Pro"
Dann ist es möglich, die C-Control als ganz normalen ATmega32 zu
verwenden.
Man muss zwar alle in CompactC fertig implementierten Funkionen neu
schreiben (z.B. die für das LCD), aber der Aufwnad lohnt sich
normalerweise.
Grüße,
Peter
So, also das mit den grauen Zellen anstrengen ist ja gut und super, aber
als Anfänger kann man halt nunmal nicht alles gleich wissen und können.
>Und deine Kommentierung.>Spar sie dir. So wie du kommentierst ist das sinnlos.
Danke für die Info, aber hier wäre auch konstruktive Kritik besser, als
nur herummosern. Was mache ich falsch?
Das mit dem Compiler wechseln werde ich mal abklären ob das möglich ist,
einen komplett anderen Controller nehmen ist nämlich nicht mehr möglich,
da die Hardware schon komplett steht.
Karl heinz Buchegger schrieb:> Und deine Kommentierung.> Spar sie dir. So wie du kommentierst ist das sinnlos.
Finde ich nun nicht, wenn es für IHN so hilfreich ist zu verstehen was
er da eigentlich macht... ist das schon in Ordnung.
Florian K. schrieb:> Danke für die Info, aber hier wäre auch konstruktive Kritik besser, als> nur herummosern. Was mache ich falsch?
Lass dich da mal nicht durcheinanderbringen, bei den Comment ist es halt
wichtig das DU damit zurecht kommst. Als Gedankenstütze ist das sehr
hilfreich!
Es ist nicht nur die Qualität des Werkzeuges mit der man arbeitet.
Ein Programm ist zum großen Teil nur so gut wie der Stil seines
Programmierers.
Deshalb ist es vorallem in der embedded Programmierung wichtig bei den
Grundlagen zu beginnen und die Beziehung zwischen Hard & Software zu
kennen und zu verstehen. Das wirkt sich dann auch entsprechend auf den
Programmcode aus.
Das ist im übrigen nicht nur eine Erfahrung die einem in der
Softwareentwicklung begleitet sondern im gesamten Lebensablauf.
Hatte erst kürzlich ein typisches Beispiel, bei dem ein MSP430F169 in
Java
programmiert wurde. Es sollten lediglich 24 LEDs geschaltet werden,
Kommandogesteuert über UART 19200 Baud.
Der Programmierer meinte, die MCU sein dazu zu schwach.
Ich denke ein Intel ATOM wäre für diese Applikation angebracht.
Leider tummeln sich heute in vielen Bereichen sogenannte Pseudo-Profis
die selbst ohne Bezahlung zu viele Schäden anrichten.
Rubelus schrieb:> Karl heinz Buchegger schrieb:>> Und deine Kommentierung.>> Spar sie dir. So wie du kommentierst ist das sinnlos.>> Finde ich nun nicht, wenn es für IHN so hilfreich ist zu verstehen was> er da eigentlich macht... ist das schon in Ordnung.
Solange er im Kommentar nur dsas hinschreibt, was sowieso im Quelltext
auch schon steht, ist das sinnlos.
Florian K. schrieb:> So, also das mit den grauen Zellen anstrengen ist ja gut und super, aber> als Anfänger kann man halt nunmal nicht alles gleich wissen und können.
Das Problem ist, dass eines der ersten Dinge, praktisch gesehen 2.
Unterrichtsstunde, in der C Programmierung darin besteht, wie man in
einen Ausgabestring variable Dinge wie Zahlen oder Variablen einbaut.
Das heißt, das IST Anfängerwissen. Wenn ein Anfänger sonst nicht viel
von C versteht, aber wie man Zahlen ausgibt und in einen Text einbettet,
das weiß er.
> Danke für die Info, aber hier wäre auch konstruktive Kritik besser, als> nur herummosern. Was mache ich falsch?
Deine Kommentare erzählen gegenüber dem eigentlichen Code nichts neues.
LCD_CLR(); //LCD löschen
LCD_Locate_Ext(1,1); //Zeile 1, Pos 1
Hier steht im Kommentar exakt dasselbe, was auch im Quelltext steht.
Wenn die Funktion nicht LCD_CLR heißen würde, sondern LCD_Clear dann
wäre es noch offensichtlicher. Das bedeutet (und ich weiß schon, da
kannst du nichts dafür) dass unter Umständen die Funktionen mit
schlechten Namen versehen wurden, wenn du dir da im Kommentar
dazuschreiben musst, was die Funktion macht.
Kommentare sollen das 'Warum' erzählen und nicht das 'Wie'. Das 'Wie'
steht im Quellcode und wenn es dort nicht ersichtlich ist, dann ist die
richtige Vorgehensweise darin zu suchen, den Code so zu schreiben bzw.
zu ändern, das man das sieht.
Beispiel
AbsDelay(2000); //Verzögerung in ms
Du hast dir hier im Kommentar hingeschrieben, dass die Zeit in
Millisekunden angegeben wird. Das ist gut. Aber auch schlecht. Denn wenn
die Funktion nicht AbsDelay sondern AbsDelayMs heißen würde, dann würde
bereits im Funktionsnamen die Information enthalten sein, für die du
hier einen Kommentar als notwendig erachtet hast.
Jeder Kommentar, den du nicht brauchst, weil dieselbe Information schon
im QUelltext enthalten ist, ist ein guter Kommentar :-)
Denn was ist das Problem?
Das Problem, wenn im Kommentar prinzipiell dasselbe steht wie im
Quelltext, besteht darin, dass es öfter als man glaubt passiert, dass
Quellcode und Kommentar nicht zusammenstimmen. Es ist noch gar nicht
solange her, da konnte man hier im Forum lesen
if( Wert == 29 ) // Wenn der Wert nicht gleich 29 ist
Genau hier haben wir zb eine Situation
* Im Kommentar steht prinzipiell genau das gleiche wie im Quellcode
* Aber: die beiden widersprechen sich! Im Kommentar steht das genaue
Gegenteil vom eigentlichen Code.
Und da fragt man sich jetzt: Was stimmt denn nun? Was ist denn richtig?
Wenn der Kommentar sinnvoll gewesen wäre
if( Tag == 29 ) // Wir wissen: Der Monat ist Februar
// damit ist der 29. Februar ein Sonderfall
// da er nur in Schaltjahren existiert
dann erzählt mir der Kommentar, warum hier eine Abfrage existiert,
welchen Grund es dafür gibt, was der Hintergedanke dabei ist und ich
kann im Zusammenhzang des Codes viel leichter entscheiden ob das == da
jetzt richtig ist, oder ob es != hätte heißen müssen.
Der erste Kommentar der beiden war ein sinnloser Kommentar. Er erzählt
mir nichts, was ich nicht auch im Code sehen würde. Der zweite Kommentar
ist ein guter Kommentar. Er erzählt mir worum es an dieser Stelle im
Code geht.
Gerade Anfänger denken oft (oder ihnen wird erzählt), dass man jede
Zeile kommentieren soll. Und dann kommen solche Dinge raus, wie in
deinem Eröffnungsposting. Im Grunde sieht es aus wie in einem
Vokabelheft: Links steht das englische Wort, rechts die deutsche
Übersetzung dazu. Genau so sollte Kommentierung aber nicht aussehen,
denn das ist sinnlose Kommentierung - Tipparbeit für nichts. Im
Idealfall lernt man nichts über den Code wenn man die Kommentare liest.
Im schlechtesten Fall ist der Kommentar einfach nur falsch.
In diesem Sinne: Wiederhole in deinen Kommentaren nicht das, was du auch
im Code siehst, sondern das was ich eben nicht im Code sehen kann!
Oder eben in Kurzform: Ein Kommentar erzählt mir das "Warum". Das "Wie"
steht im Code. Wenn du das Gefühl hast, du musst das "Wie" kommentieren,
dann sieh dir lieber den Code an und such nach Möglichkeiten, wie du den
Code so ändern kannst, dass er diese Information mit enthält.
Danke, jetzt wo du es schreibst ist es mir auch klar, dass diese Art von
Kommentare nichts bringen, man wiederholt nur dass was eh schon da
steht.
Werde jetzt die Funktionen mal besser benennen und die restlichen
Kommentare anpassen, bzw. löschen