Hallo zusammen, ich programmiere nicht mit dem gcc sondern mit MPLab und dem Hi-Tech Pic16 C-Compiler. Aber ich denke und hoffe, dass ihr mir weiterhelfen könnt. Ich habe ein Struct wie folgt definiert: struct DATA{ short value1; short value2; short value3; short value4; } Werte; nun kann ich ja über das Makro offsetof die Position eines Elements im Struct herausfinden. Dies funktioniert auch mit folgendem Quelltext: offsetof(struct DATA, value2); Nun stellen die Werte value1, value2,... unterschiedliche Werte dar, welche in einem Menü verändert werden können. Dazu gibt es einen Zeiger auf den zum aktuell ausgewählten Menüpunkt zugehörigen Wert. Also der Wert welcher im ausgewählten Menüpunkt geändert werden kann wird über einen Zeiger angesprochen bspw.: short *pointer = &Werte.value2; in der Menüfunktion wird jetzt der Wert des Pointers verändert. Nun möchte ich die Position im Struct des Wertes herausfinden, auf welchen der Pointer zeigt. Dazu habe ich folgendes ausprobiert nur leider funktioniert das nicht: offsetof(struct DATA, *pointer); Der Compiler bringt mir die Fehlermeldung "Zeiger erforderlich" Kann mir hier bitte jemand weiterhelfen??? Habe ich einen Denkfehler oder geht das einfach nicht? Gibt es einen anderen Weg??? Vielen Dank schon im Vorraus!!! Flo
Das scheint eher eine Aufgabe für ein Array statt ein struct zu sein. Fragender schrieb: > offsetof(struct DATA, *pointer); > > Der Compiler bringt mir die Fehlermeldung "Zeiger erforderlich" Das zweite Argument für das Makro muss der Name eines Elements sein. So geht das nicht. Um nur die Differenz zweier Zeiger zu erhalten, muss man sie voneinander abziehen (so weit, so offensichtlich). Allerdings erhält man die Differenz in Einheiten der Datenobjekte, auf die gezeigt wird. Wenn die Differenz in Bytes gewünscht wird, muss man beide Zeiger nach char* casten. Mit Arrays ist alles viel einfacher:
1 | short Werte[4]; |
2 | |
3 | short *pointer = &Werte[1]; |
4 | |
5 | int index = pointer - Werte; |
Vielen Dank! Habe aber leider nicht gesagt, dass im Struct nicht nur shorts, sondern auch andere Datentypen sind. Deshalb doch leider Struct. Mit einem Array habe ich es zuvor implementiert und das hat auch funktioniert. Dann müsste es doch aber folgendermaßen funktionieren: unsigned char *offset = (unsigned char)pointer - &(unsigned char)Werte Flo
Die Frage ist immer noch: WOZU? Etwas derartiges hab ich in 30 Jahren noch nie benötigt. (Mit scheint nämlich, du zäumst das Pferd von der falschen Seite auf)
Fragender schrieb: > Habe aber leider nicht gesagt, dass im Struct nicht nur shorts, sondern > auch andere Datentypen sind. Deshalb doch leider Struct. Mit einem Array > habe ich es zuvor implementiert und das hat auch funktioniert. Man kann ein Array auch als Element von einem struct definieren… Fragender schrieb: > Dann > müsste es doch aber folgendermaßen funktionieren: > > unsigned char *offset = (unsigned char)pointer - &(unsigned > char)Werte Das funktioniert überhaupt nicht. Und ich habe in meinem Beispiel die Variable nicht offset, sondern index benannt — aus dem Grund, dass es den Index ins Array ergibt und nicht den Byte-Offset. Wenn du den willst, musst du den Index einfach mit der Elementgröße, hier "sizeof (short)", multiplizieren.
Verwende ein Pointer als pointer, und nicht deren Inhalt !!!. Dein falscher Code: offsetof(struct DATA, *pointer); sollte lauten offsetof(struct DATA, pointer); Wenn du überlegst warum, wirst du warscheinlich auch erraten wieso.
Es stimmt, daß eine solches coding merkwürdig ist und im allgemeinen vermieden wird, zumindest für das Beispiel das du uns erbracht hast.
Chris schrieb: > Verwende ein Pointer als pointer, und nicht deren Inhalt !!!. > Dein falscher Code: > offsetof(struct DATA, *pointer); > > sollte lauten > offsetof(struct DATA, pointer); Das funktioniert genauso wenig, pointer ist kein Name eines Elements von struct DATA.
Stimmt, sorry. Wenn pointer ein member von Werte ist, kannst du ptrdiff anstelle von offsetoff verwenden, sofern definiert. Ansonsten einfach #define ptrdiff(x,y) (((unsigned int)&x)-(unsigned int)&y) Ansonsten, geht nicht.
Dass das ganze merkwürdig ausschaut und weshalb man soetwas eigentlich nicht verwenden sollte lasse ich mir gerne auch erklären, verstehe zwar nicht warum aber naja. In meinem Fall macht es aber Sinn, da es weniger Speicherplatz benötigt (habs getestet) und auch einfacher erweiterbar ist!!! Habe das Problem übrigens folgendermaßen gelöst und es funktioniert: unsigned char offset = (unsigned char*)pointer - (unsigned char*)&Werte Vielen Dank an alle!!! Flo
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.