Hallo zusammen, ich habe eine Frage bezüglich einer Umwandlung von einer Zahl zu einem String. Hier der Code: void LCD_PrintZahl16 (unsigned int zahl) { int i; unsigned char tempstring[6]; unsigned char schonzahl = 0; for (i = 5; i>= 0 ; i--) // Umwandeln einer Zahl in einen String (nur 6 Ziffern möglich, deswegen von 5 bis 1) { tempstring [i] = ((zahl % 10) | 0x30); // zahl = zahl / 10; } for (i = 1; i <= 5; i++) // führende Nullen durch BLANK ersetzen { if ((tempstring [i] == 0x30) && (schonzahl == 0) && (i <= 4)) tempstring [i] = 0x20; //Leerzeichen else schonzahl = 1; } for (i = 1; i <= 5; i++) // Ausgabe { LCD_write_data (tempstring [i]); } } Es wird die Zahl eines Drehencoders über I2C an einem DIsplay ausgegeben. Hier ist mir folgendes nicht verständlich. 1. tempstring [i] = ((zahl % 10) | 0x30); // zahl = zahl / 10; 2. Ascii 0x30 ist doch eine Null. Und was ist Ascii 0x20 (in der Tabelle steht SP)? Ich weiß, dass es bestimmt auch anders geht. Trotzdem ist es mir hilfreich auch diese Fragen zu klären. Für sinnvolle Antworten bedanke ich mich schon jetzt. Gruß
> 1. tempstring [i] = ((zahl % 10) | 0x30); // > zahl = zahl / 10; 23 % 10 = 3 3 + 0x30 = '3' bzw. Dezimalzahl 3 + ASCII-Zeichen '0' = ASCII-Zeichen '3' 23 / 10 = 2 ... > 2. Ascii 0x30 ist doch eine Null. Und was ist Ascii 0x20 (in der Tabelle > steht SP)? 0x20 = ASCII-Zeichen SP, SPACE, Leerzeichen, ' '
kommen da nicht strings wie 0 13 raus ? es werden zwar die ziffern von 0 bis 5 bestimmt, aber nur die ziffern 1 bis 4 potentiell durch ' ' ersetzt. Oder seh ich da was falsch? Edit: ok, hab grad gesehen, dass tempstring[0] nie ausgegeben, also irellevant ist...
Judgin F. schrieb: > zahl = zahl / 10; > } > for (i = 1; i <= 5; i++) // führende Nullen durch BLANK ersetzen > { if ((tempstring [i] == 0x30) && (schonzahl == 0) && (i <= 4)) > tempstring [i] = 0x20; //Leerzeichen > else > schonzahl = 1; > > } > for (i = 1; i <= 5; i++) // Ausgabe > { LCD_write_data (tempstring [i]); > } > } > Es wird die Zahl eines Drehencoders über I2C an einem DIsplay > ausgegeben. > Hier ist mir folgendes nicht verständlich. > > 1. tempstring [i] = ((zahl % 10) | 0x30); // > zahl = zahl / 10; > > 2. Ascii 0x30 ist doch eine Null. Und was ist Ascii 0x20 (in der Tabelle > steht SP)? > Du hast gerade rausgefunden, warum diese Schreibweisen verpönt sind. Erstens gibt es keinen Grund dafür, hier Hex-Ziffern zu nehmen und zweitens muss man dann einen Kommentar dazuschreiben fpr etwas, was man im Code genausogut hätte schreiben können Anstelle von > tempstring [i] = ((zahl % 10) | 0x30); // Schreibt mal tempstring [i] = (zahl % 10) + '0'; Und anstelle von > tempstring [i] = 0x20; //Leerzeichen schreibt man tempstring [i] = ' '; Kein Mensch braucht mehr die Kommentare oder gar eine ASCII Tabelle um nachzusehen, für welche Zeichen die Codes 0x30 bzw. 0x20 eigentlich stehen :-)
Der ganze Code schreit danach, weggeworfen zu werden (falls er für einen 8-Bit µC gedacht ist)
Judgin F. schrieb: > Hier der Code: > void LCD_PrintZahl16 (unsigned int zahl) Hast du mal nachgeschaut, wie Andere das machen? Es gibt fertige optimierte Bibliotheken für solche Trivialaufgaben. Wozu das Rad neu erfinden?
@ Lothar Miller (lkmiller) Benutzerseite >Hast du mal nachgeschaut, wie Andere das machen? So schlecht ist sein Ansatz nicht. > Es gibt fertige >optimierte Bibliotheken für solche Trivialaufgaben. Wozu das Rad neu >erfinden? Lernen? MFG Falk
Falk Brunner schrieb: >> Es gibt fertige >>optimierte Bibliotheken für solche Trivialaufgaben. Wozu das Rad neu >>erfinden? > > Lernen? Lernen was die C API bietet macht aber auch Sinn. @Judgin F.: Gibt es einen besonderen Grund warum du nicht itoa() benutzt? Siehe: http://www.mikrocontroller.net/articles/FAQ#Wie_kann_ich_Zahlen_auf_LCD.2FUART_ausgeben.3F
Udo Schmitt schrieb: > Gibt es einen besonderen Grund warum du nicht itoa() benutzt? Weil es mit itoa ziemlicher Aufwand ist, führende 0-en bzw führende Leerzeichen auf eine konstante Feldbreite zu ergänzen. Und die zu haben, ist bei LCD Ausgaben meistens nicht das Schlechteste.
Udo Schmitt schrieb: > Lernen was die C API bietet macht aber auch Sinn. > @Judgin F.: > Gibt es einen besonderen Grund warum du nicht itoa() benutzt? itoa() gehört aber eben gerade nicht zum C Standard ;-)
Karl Heinz Buchegger schrieb: > Weil es mit itoa ziemlicher Aufwand ist, führende 0-en bzw führende > Leerzeichen auf eine konstante Feldbreite zu ergänzen. > Und die zu haben, ist bei LCD Ausgaben meistens nicht das Schlechteste. Stimmt Mark Brandis schrieb: > itoa() gehört aber eben gerade nicht zum C Standard ;-) Jepp, aber in dem von mir angegebenen Link auf die FAQs steht daß sie in WinAVR verfügbar ist. :-) Egal, Karl Heinz und Falk haben ja auch recht. Selber machen übt.
Für welchen uC ist das Programm gedacht? Manche können gar nicht dividieren, das heißt, es wird dann intern ein ziemlicher Aufwand getrieben, um sowas wie "i/10" zu rechnen. Wenn es gleichzeitig eine zeitkritische Anwendung ist, sollte man itoa() vielleicht ohne Division programmieren.
@Markus W Ist ein Atmega168, der kann das schon. @alle Danke dür die hilfreichen Tipps. Ich habe jetzt meinen Vorschlag und das itoa noch einmal durchgearbeitet. Beides ist klar. @ die, die das selbe Problem haben, oder haben werden. Der link vom Falk Brunner war dabei sehr hilfreich. Danke
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.