Shamharoth Geschrieben 14. April 2010 Geschrieben 14. April 2010 hallo zusammen. zur zeit schreib ich rechd viele fragen, aber mir fallen sachen ein, die ich nich brauch und mir fallen sachen nicht ein, die ich einfach brauch. situation: eine funktion hat n void-pointer. dieser wird je nach anlass zu nem struct gecastet (verschiedene). frage: ist es möglich neben prüfung ob dieser NULL ist auch das prüfen ob es die richtige struct ist? ansonsten kann man ja den größten blödsin casten ^^ Zitieren
Klotzkopp Geschrieben 14. April 2010 Geschrieben 14. April 2010 ist es möglich neben prüfung ob dieser NULL ist auch das prüfen ob es die richtige struct ist?Nein. Grundsätzlich gilt beim Casten, dass man genau wissen muss, was man tut, weil man damit Fehlerprüfungen durch den Compiler abschaltet. Zitieren
lilith2k3 Geschrieben 14. April 2010 Geschrieben 14. April 2010 Gegenfrage: wie soll das funktionieren? Der Compiler kann ja schließlich nicht hellsehen... Stell Dir die Sache mal bildlich vor: Ein Void-Pointer ist quasi wie ein Notizzettel. Ich schreibe Dir einen Zettel auf dem steht, daß Du bitte in den Keller gehen sollst, mir den Inhalt meines Schuhkartons Nummer 3 mitbringen sollst. Nun darfst Du anhand des Zettels erraten, was genau ich haben will ... Zitieren
Shamharoth Geschrieben 15. April 2010 Autor Geschrieben 15. April 2010 schad schad ..... das blöde man kann ja auch keine feste werte dem vorinitialisieren ... sonst hätte ich dem direkt ne "id" verpassd :/ würde ich die bib nur für C++ un nich noch für C schreiben, könnte ich klassen machen ... aba so :/... danke trotzdem ^^ Zitieren
TDM Geschrieben 15. April 2010 Geschrieben 15. April 2010 situation: eine funktion hat n void-pointer. dieser wird je nach anlass zu nem struct gecastet (verschiedene). frage: ist es möglich neben prüfung ob dieser NULL ist auch das prüfen ob es die richtige struct ist? Übergib doch einfach noch n enum-Werte, um welchen Typ es sich bei der data[n]:type[n]-Verbindung handelt. :floet: Zitieren
Klotzkopp Geschrieben 15. April 2010 Geschrieben 15. April 2010 würde ich die bib nur für C++ un nich noch für C schreiben, könnte ich klassen machen ... aba so :/...Wenn du Klassen als Void-Zeiger übergibst, hast du dasselbe Problem. In C++ könntest du das Problem vielleicht eher durch Überladung lösen. Kannst du nicht für jede Struktur eine eigene Funktion einführen? Zitieren
Shamharoth Geschrieben 15. April 2010 Autor Geschrieben 15. April 2010 Wenn du Klassen als Void-Zeiger übergibst, hast du dasselbe Problem. *Mein Post noch mal durchles* K ich habs etwas ungenau geschrieben. Das mit den Klassen is auf die vordefinierte Variable bezogen Ansonste hätte ich sicherlich die gleiche Probleme wie bei Strukturen In C++ könntest du das Problem vielleicht eher durch Überladung lösen. Kannst du nicht für jede Struktur eine eigene Funktion einführen? Also dass ich entsprechend der struktur, die übergeben wird eine entsprechende funktion schreib? Problem ist ja, dass daas Programm unter C laufen soll, kann eine Überladung nicht eingesetzt werden (deswegen void*) würde ich explizit für jede Art a funktion schreiben (mit entsprechenden funktionsnamen) ist bei der bibliothek nach aussen hin mehrere Funktionen sichtbar. Dies wollte ich jedoch vermeiden. Nach aussenhin gibt es nur eine Funktion, die aufgerufen werden kann. Zitieren
Klotzkopp Geschrieben 15. April 2010 Geschrieben 15. April 2010 würde ich explizit für jede Art a funktion schreiben (mit entsprechenden funktionsnamen) ist bei der bibliothek nach aussen hin mehrere Funktionen sichtbar. Dies wollte ich jedoch vermeiden.Warum? Zitieren
Shamharoth Geschrieben 15. April 2010 Autor Geschrieben 15. April 2010 weils schöner aussieht Ne... Das is leider eine vorgabe vom Projekt Zitieren
frobber Geschrieben 22. April 2010 Geschrieben 22. April 2010 (bearbeitet) Da nach deinen eigenen Angaben die Möglichkeit mit mehreren Funktionen ausfällt, würde ich die Lösung von TDM in Betracht ziehen, also einen zusätzlichen Paramter übergeben welcher die Struktur identifiziert. Ich wollte hier blos nochmal eine Lösung zeigen, die Microsoft oft in iherer API verwendet. Die geben einfach jeder Struktur einen Längenparameter mit und unterscheiden anhand der Länge, um welche Struktur es sich handelt, also: struct A { unsigned Size; // sizeof(A) ... }; struct B { unsigned Size; // sizeof( ... }; Wichtig ist dabei, dass der Längenparameter immer an erster Stelle steht und die verschiedenen Strukturen auch tatsächlich eine unterschiedliche Größe haben, damit sie so überhaupt unterscheidbar sind. Die Auswertung könnte dann in etwa so aussehen: void foo(void* pData) { unsigned size = 0; struct A* pA; struct B* pB; if(pData != 0) { size = *(unsigned*)pData; if(size == sizeof(struct A)) { pA = (struct A*)pData; // ... } else if(size == sizeof(struct ) { pB = (struct B*)pData; //... } ... } } Microsoft verwendet diese Technik, um Strukturen zu unterscheiden, die sich im laufe der Zeit mal verändert haben und um einige Sachen erweitert wurden. Gruß Frobber Bearbeitet 22. April 2010 von frobber Zitieren
TDM Geschrieben 22. April 2010 Geschrieben 22. April 2010 und die verschiedenen Strukturen auch tatsächlich eine unterschiedliche Größe haben, damit sie so überhaupt unterscheidbar sind. Da man das aber nicht immer vorraussetzen kann, da erstens Datengrößen sich im späteren Verlauf unterscheiden können bzw. zweitens, die Größe der Primitives von Compiler zu Compiler variieren, würde ich das nur als suboptimale Lösung empfinden. Zitieren
frobber Geschrieben 22. April 2010 Geschrieben 22. April 2010 ... da erstens Datengrößen sich im späteren Verlauf unterscheiden können ... Du denkst dabei wahrscheinlich an eine Änderung der Daten durch dynamisches allokieren mittels 'new' oder 'malloc'. Dadurch ändert sich aber nichts an der größe der Struktur an sich, sondern lediglich quasi semantisch der Inhalt der Struktur. Dem 'sizeof(...)' Operator ist es egal. Bsp.: struct A { unsigned Size; // sizeof(A) char* pData; // dynamisch allokierter Speicher ... }; void foo() { struct A a_dummy; // instance of A unsigned i = sizeof(a_dummy); // i ist 8 a_dummy.pData = (char*)malloc(10); i = sizeof(a_dummy); // ist ist immernoch 8 } Die einmal durch Deklaration definierte Größe einer Struktur kann sich zur Laufzeit nicht ändern. zweitens, die Größe der Primitives von Compiler zu Compiler variieren In dem Punkt geb ich dir teilweise Recht, aber das ist eher eine Frage der Plattform, als eine des Compilers. Primitive Datentypen werden zwischen verschiedenen Compilern auf der selben Plattform (im Sinne von Linux, Windows, ARM) in der Regel gleich behandelt. Interessanter ist da eher die Frage nach dem Packing der Strukturen. Da kann man schnell auf Nase fallen. ...würde ich das nur als suboptimale Lösung empfinden Ja ich würde auch eher deine Lösung wählen, wenn ich nicht genau weiß was mit den Strukturen im Laufe der Entwicklung noch so passiert. Zitieren
TDM Geschrieben 22. April 2010 Geschrieben 22. April 2010 Du denkst dabei wahrscheinlich an eine Änderung der Daten durch dynamisches allokieren mittels 'new' oder 'malloc'. Eher nicht, ich dachte vielmehr an: Ja ich würde auch eher deine Lösung wählen, wenn ich nicht genau weiß was mit den Strukturen im Laufe der Entwicklung noch so passiert. Im Sinne von Remodellierung. Dann ist schwups mal Struktur C so groß wie Struktur A, weil auf einmal noch ein Charpointer Member der Struktur ist. Zitieren
Shamharoth Geschrieben 23. April 2010 Autor Geschrieben 23. April 2010 gut na dann sag ich doch mal danke ^^ ich überleg mir mal ob ich es so in das projekt einbinden kann insgesammt war es eh eher nur eine optionale idee, damit es weniger fehler auftauchen könnten wenn es benutzt werden würde. darum nochmal ein danke an alle Zitieren
Empfohlene Beiträge
Dein Kommentar
Du kannst jetzt schreiben und Dich später registrieren. Wenn Du ein Konto hast, melde Dich jetzt an, um unter Deinem Benutzernamen zu schreiben.