Umwandlung von char

wie funktioniert es wenn ich auf dem arduino in der arduino ide ein char in ein int hex wadeln will?
zb so wie hier:

int char2hex(char *zeiger, unsigned char anzahl)
{
int ret_wert=0; char n, wert;
if((anzahl >= 1)&&(anzahl <= 4)) {
for(n=1; n<=anzahl; n++) {
wert = *zeiger; ret_wert *= 0x10;
if(((wert<='9')&&(wert>='0'))||((wert<='f')&&(wert>='a'))||(wert<='F')&& (wert>='A'))
{
if((wert<='9')&&(wert>='0'))ret_wert+=wert-'0'; if((wert<='f')&&(wert>='a'))ret_wert+=((wert-'a')+10); if((wert<='F')&&(wert>='A'))ret_wert+=((wert-'A')+10);
}
else{ret_wert = -1;} zeiger++;}
}
else{ret_wert = -1;} return(ret_wert);
}

Genauso wie es auf jedem anderen Prozessor funktioniert. Auch einer Substraktion. Schau dir die ASCII Tabelle an

wie funktioniert es wenn ich auf dem arduino in der arduino ide ein char in ein int hex wadeln will?

Offensichtlich hast du schon seit geraumer Zeit ein Problem mit Zeichen, Bytes und den Umwandlungen ....

Dabei ist das doch gar nicht so schwer...

Wichtig ist: Die genaue Definition der Eingangsdaten. Eine genaue Definition dessen, wie sie hinterher aussehen sollen.

Und nein, das Wort "Hexzahlen" ist da nicht hilfreich. Denn: Die Hexzahlen entstehen im Kopf, bei der Betrachtung.

Hexadezimal ist nur eine Repräsentation der Daten. So wie Dezimalzahlen auch nur eine Repräsentation ist.

Char Dezimal und Hex sind nur Repräsentationen der u.U. selben Daten. Ein Erscheinungsbild. Vielgesichtig, aber im Kern das gleiche.


Du bastelst da schon so lange dran rum(Monate?), dass ich vermuten muss dass da eine tiefe Fehldenke vorliegen muss. Leider weiß ich nicht wie und wo. Ich sehe deinen Irrtum nicht.

Wie kann ich dir helfen, diese Hürde zu überwinden? Dauerhaft zu überwinden!

ich glaube wirklich das ich komplett fehldenke. ich habe verstanden das im grunde genommen hex, dez nur darstellung ist ob ich jetzt 1 in ascii oder 31 in hex schreib ist ja nur darstellung.

Aber wenn ich das auch richtig versteh gibt es einen Unterschied zwischen int hex und char hex. oder versteh ich das falsch?

das nächste ist wenn ich über die Serial am arduino eine hexzahl versenden will wie funnktionniert das? kann ja nicht einfach an der Stelle von 1 eine 31 senden? er senet mir dann ja eine 31 in ascii.

Du hast eine Variable mit 49 dezimal. Was willst Du versannt haben?

0x31 in HEX oder die "1" ?

Grüße Uwe

Welchen Unterschied soll es da geben? Das sind letztlich alles nur Integer. Auch char ist nur ein Byte mit Vorzeichen

das nächste ist wenn ich über die Serial am arduino eine hexzahl versenden will wie funnktionniert das?

Wenn es um ASCII geht schau dir die ASCII Tabelle an http://www.asciitable.com/

Wenn es im Binärwerte geht schau dir Serial.write() an

Und lerne den Unterschied zwischen ASCII Zeichen und Binärdaten!

0x31 will ich versenden

Serial.write(0x31)

Wo ist da das Problem? Dafür brauchst du gar kein ASCII. ASCII ist relevant z.B. wenn man Zeichen im seriellen Monitor eintippen will. Um einfach Integer zu senden, verwendet man write()

Und nochmal: wenn du ein Datenblatt hast und das sagt, dass es 0x31 möchte, dann ist das nur eine Darstellungssache. Das wird so geschrieben, weil man es einfacher lesen kann und sofort die Bit-Darstellung sieht. Das heißt nicht dass man da irgendwas besonders formatieren muss oder "Hex schicken muss". Letztlich will das Gerät einfach nur 8 Bits.

Bei sowas musst du aber generell verschiedene Anwendungsfälle unterscheiden: 1.) Daten von einem Gerät einlesen 2.) Daten von einem seriellen Terminal einlesen 3.) Daten zu einem Gerät senden 4.) Daten auf ein serielles Terminal ausgeben

1.) und 3.) kann entweder ASCII oder Binär sein, je nach Anwendung. 2.) und 4.) ist ist aller meistens ASCII, vor allem mit dem seriellen Monitor der IDE

gibt es einen Unterschie zwischen

Serial.write(0x31)

und char test="4"; Serial.print(test);

nein oder?

write() sendet Binär. print() sendet ASCII

Generell kannst du mit print() auch längere Zahlen auf ASCII formatieren (z.B. long oder float) und es gibt auch in paar einfache Formatierungs-Optionen. write() kann nur entweder ein einzelnes Byte senden oder ein Array aus Bytes.

char test="4" ist Unsinn. Ein char ist ein einzelnes Zeichen. Das kommt in einfache Anführungszeichen:

char test= '4';

"4" ist ein C String. Das sind zwei Bytes. Einmal '4' und einmal NULL um den String zu terminieren. C Strings sind Arrays aus char

ok mich wunder das nur wenn ich über meinen arduino an einen rs232 monitor Serial3.write(0x31) sende kommt das so an

Read data 31 1

Wenn ich wie oben char test="1" mach und dann Serial3.print(test)

kommt auch

Read data 31 1

Wo liegt da jetzt der Unteschied

nomis321: Wenn ich wie oben char test="1" mach und dann Serial3.print(test)

Mein Compiler (IDE 1.6.5) beschwert sich:

invalid conversion from 'const char*' to 'char' [-fpermissive]

Keine Idee, wie Du zu Deinem Ergebnis kommst.

write(0x31) und print(‘1’) ist natürlich das gleiche. 0x31 ist nunmal der Wert von ‘1’ in ASCII

Lade dir mal HTerm herunter. Das ist ein komplexeres Terminal Programm mit dem du komplette Kontrolle über die Zahlendarstellung hast. Sowohl beim Senden als auch beim Empfang.

Dann nimm ein einfaches Programm wie das:

void setup()
{
 Serial.begin(9600);

 Serial.write(0x31);
 Serial.print(0x31);
 Serial.print("0x31");
}

void loop()
{
}

Da das Programm nur einmal nach dem Reset sendet, musst du den entweder auf dem Arduino mit dem Taster auslösen oder in HTerm durch das DTR Signal (bei Input Control)

Auf dem Bild im Anhang siehst du genau was abläuft. Hellblau ist ASCII. Lila ist Hex. Rot ist Dezimal. Grün ist Binär

write(0x31) sendet einfach den Integer 0x31. 49 in Dezimal. Wenn du dir mal die Binärdarstellung ansiehst, merkst du vielleicht auch wieso Hex so oft verwendet wird. Jede Ziffer enspricht 4 Bit. Die obersten 4 Bit sind 3. Die unteren 4 Bit sind 1.

print(0x31) interpretiert die Zahl erst mal als Integer und sendet diese in ASCII. Aber Dezimal formatiert! Es kommt “49” in ASCII. Was zwei Bytes mit 34 und 39 sind (siehe ASCII Tabelle)

print(0x31, HEX) formatiert die Zahl Hexdezimal. Es ist immer noch ASCII, aber nun hat man wirklich 31. Also zwei Bytes mit 33 und 31

print(“0x31”) sendet den String so wie er ist. Also 4 Bytes mit den entsprechenden ASCII Werten

ok danke ich hätte da mal aber noch was anderes ein komando welches ich in hex über mitteln will hat ja nicht nur eine zahl.

ist ja z.B 49f0 + checksumme [

also 49f0[

dies würde dann ja in hex 343966305b entsprechen

wie kann ich jetzt das ganze in serial.write packen?

will ja nicht einzeln Serial.write(0x34) Serial.write(0x39) Serial.write(0x66) Serial.write(0x30) Serial.write(0x5b)

schreiben.

sondern das bei tastendruck eine z.b 49f0[ und bei tastendruck 2 49f9r gesendet wird(über serial.write)

Ich haben oben schon gesagt, dass write() entweder ein Byte oder ein Array senden kann. Das ist auch ersichtlich wenn du mal in die Arduino Referenz zu write() schaust: https://www.arduino.cc/reference/en/language/functions/communication/serial/write/

Du kannst also sowas machen:

byte code1[] = { 0x34, 0x39, ... };  //hier kann man statt 0x34 auch '4' schreiben

...

Serial.write(code1, sizeof(code1));

Es gibt sicherlich auch noch andere Optionen.

write("49f0") und ein zusätliches write() für die Checksumme geht vielleicht auch. Damit hat man im Code eine Darstellung als ASCII. Was da besser ist, ist teils Geschmackssache. Am einfachsten ist es sicherlich die Darstellung im Code in Einklang mit der Darstellung im Datenblatt des Geräts zu bringen

Aber wenn du dann schon wieder sowas schreibst:

ich hätte da mal aber noch was anderes ein komando welches ich in hex

Ich dachte es wäre inzwischen mal klar dass mit dem Senden rein gar nichts zu tun hat sondern nur eine Dartstellungssache ist

Oder anstelle code1, code2 ... nimmst Du ein zweidimensionales Feld mit allen Codes.

Hi

Was willst Du eigentlich mit den HEX-Zahlen?
Werden Die ‘am anderen Ende’ wieder zu einem Word zusammen gebaut?
Also wird aus ‘4’ ‘9’ ‘f’ ‘0’ später eine 0x49F0?
Erwartet ‘das andere Ende’ ggf. einfach nur ein Word (2 Byte)?
Also 0x49 0xF0?

Den ganzen Kram hatten wir hier, vor gar nicht all zu langer Zeit mit genau diesen beiden HEX-Zahlen, wo ich mich jedes Mal ärgere, daß der Buchstabe klein geschrieben wird.
(kein Thema, von Zahlzeichen 0-9 kann man 0x30 abzehen, wenn>9 0x07, wenn > 15 0x20 und man kommt auf die übermittelte Ziffer … sofern Diese jetzt <0 oder >15 ist, war’s doch kein Hex-Zahl-Zeichen)

Gibt es zu dem Problem, 4 Zeichen seriell zu übermitteln, Hintergrundwissen, was mir hier helfen könnte?
Ein Datenblatt??

MfG

nomis321: ok danke ich hätte da mal aber noch was anderes ein komando welches ich in hex über mitteln will hat ja nicht nur eine zahl.

ist ja z.B 49f0 + checksumme [

also 49f0[

dies würde dann ja in hex 343966305b entsprechen

wie kann ich jetzt das ganze in serial.write packen?

Du unterscheidest immer noch nicht zwischen Repräsentation und Inhalt. Bzw mischt du das.

Und genau damit fällst du auf die Nase.

Merke: Alles was du auf dem Seriellen Monitor siehst ist char, muss char sein, weil das Ding nur Buchstaben zeigen kann. Nichts anderes. Nur char/Buchstaben. (wenn ich mal die Repräsentation der Zahlen, zu den Buchstaben zählen darf)

Dass manche von diesen Buchstabenkombinationen wie HEX aussehen, passiert in deinem Kopf. Du bist der Interpreter. Du entscheidest, ob das 'f' Teil einer Hex Repräsentation, oder Teil des Wortes "offen" ist. Der Betrachter entscheidet. Aber im seriellen Monitor ist es immer ein char.

Serial.print(variable, HEX) gibt den numerischen Wert in Hexadezimaldarstellung aus.
Ist es das was Du wolltest?
Grüße Uwe

ich habe jetzt mal von meinem arduino an putty gesendent über rs232
gibt es auch eine Möglichkeit wie ich überprüfen kann ob ich daten empfange?
ich glaub da hab ich nehmlich ein Prblem.

ich will über den Serialmonitor ausgeben was ich über Serial3 auf meinem arduino empfang.
ich hab mir das wie folgt vorgestellt:

void setup()
{
  Serial.begin(115200);
  Serial3.begin(115200);
}

void loop()
{
 if (Serial3.available()<0)
 {
  Serial.write(Serial3.read());
 } 
}

Das müsste ja so funktionieren?
Wie kann ich das am einfachsten überprüfen.