After passing a void* pointer as argument to a function, is there a way to specify the type to which it is cast as another parameter. If I have two structs like:
struct A{
int key;
char c;
}
struct B {
int key;
float d;
}
Is it possible to define a function,
void func(void * ptr, ...){
//operate on key
}
and pass a pointer to either structs to the function after casting to void* and access the key element from within the function.
Trying to understand the use of void*, how structure definitions are stored ( How are the offsets of various elements determined from the structure definition? ) and how ploymorphism may be implemented in c.
Was trying to see if I could write Binary Search tree functions that could deal with nodes of any struct.
After passing a void* pointer as argument to a function, is there a way to specify the type to which it is cast as another parameter.
Yes and no.
I suppose you're hoping for something specific to this purpose, such as a variable that conveys a type name that the function can somehow use to perform the cast. Something along the lines of a type parameter in a C++ template, or a Java generic method, for example. C does not have any such thing.
But of course, you can use an ordinary integer to convey a code representing which of several known-in-advance types to cast to. If you like, you can even use an enum
to give those codes meaningful names. For example:
enum arg_type { STRUCT_A_TYPE, STRUCT_B_TYPE };
void func(void *ptr, enum arg_type type) {
int key = 0;
switch (type) {
case STRUCT_A_TYPE:
key = ((struct A *) ptr)->key;
break;
case STRUCT_B_TYPE:
key = ((struct B *) ptr)->key;
break;
default:
assert(0);
}
// ...
}
Note well that that approach allows accessing any member of the pointed-to structure, but if you only want to access the first member, and it has the same type in every structure type of interest, then you don't need to know the specific structure type. In that particular case, you can cast directly to the member type:
void func(void *ptr) {
int key = *(int *)ptr;
// ...
}
That relies on C's guarantee that a pointer to any structure, suitably cast, points to that structure's first member.
Trying to understand the use of void*, how structure definitions are store and how ploymorphism may be implemented in c.
That's awfully broad.
C does not offer polymorphism as a language feature, and C objects do not carry information about their type such as could be used to dispatch type-specific functions. You can, of course, implement that yourself, but it is non-trivial. Available approaches include, but are not limited to,
passing pointers to functions that do the right thing for the type of your data. The standard qsort()
and bsearch()
functions are the canonical examples of this approach.
putting some kind of descriptor object as the first member of every (structure) type. The type of that member can be a structure type itself, so it can convey arbitrarily complex data. Such as a vtable. As long as it is the first member of all your polymorphic structures, you can always access it from a pointer to one of them by casting to its type, as discussed above.
Using tagged unions of groups of polymorphic types (requiring that all the type alternatives in each group be known at build time). C then allows you to look at any members of the common initial sequence of all union members without knowing which member actually has a value. That initial sequence would ordinarily include the tag, so that you don't have to pass it separately, but it might include other information as well.
Polymorphism via (single-)inheritance can be implemented by giving each child type an object of its parent type as its first member. That then allows you to cast to (a pointer to) any supertype and get the right thing.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With