Empresas
Empleos
  • Sobre nosotros
  • Soluciones
    • Publicación de vacantes
      Publica tu vacante y recibe candidatos calificados en 48h.
    • Evaluación de candidatos
      500+ pruebas técnicas y psicológicas, más anti-fraude.
    • Headhunting
      Búsqueda ejecutiva a la medida de principio a fin.
    • Nómina + EOR
      Dispersión de nómina y EOR en más de 15 países de LATAM.
  • Precios
  • Empleos

0

293
Vistas
Cómo verificar el tipo de estructura en C

Hice una estructura de listado simple en C que contiene cualquier tipo de datos usando el puntero void*, algo así como:

 struct node { void *the_data; node *next; };

Funciona bien, pero tengo algunas listas que contienen, por ejemplo, solo struct_a en una lista y solo struct_b en otra lista. Necesito verificar si el primer elemento de la lista es del tipo struct_a o struct_b en una sola pregunta if() para saber los datos que contiene esta lista. ¿Como hacer esto? Gracias

Editar:

Se me ocurrió una solución simple que es suficiente para el problema ahora, no sé si es la mejor:

 struct node { void *data; node *next; }

Y agregué un nodo "descriptor", que contiene la dirección del primer nodo e información sobre el tipo:

 struct list_desc { node *list; short int type; }

y lo usaré con algunas macros como

 #define __data_type1 10 #define __data_type2 20

para que luego pueda comparar like if( struct.type == __data_tipe1 ) etc...

over 4 years ago · Santiago Trujillo
3 Respuestas
Responde la pregunta

0

C no proporciona información de tipo de tiempo de ejecución. Tienes que añadir esta información tú mismo. Hay dos enfoques básicos (asumiendo C99 o C11):

Puede usar una estructura (potencialmente) con unión anónima:

 struct Node { enum { OBJ_TYPE_A, OBJ_TYPE_B } type; union { struct NodeA a; struct NodeB b; }; // anonymous, if a name is added, you have an additional field name }; ... struct Node *node = ...; if ( node->type == OBJ_TYPE_A ) { node->a.a_field = whatever; ...

Las desventajas son que debe definir la unión en un solo lugar y no puede extenderla en otro módulo.


Un mejor enfoque es construir una verdadera jerarquía de clases con estructuras anónimas:

 struct Node { enum { OBJ_TYPE_A, OBJ_TYPE_B } type; struct Node *next; }; struct NodeA { struct Node; // base class, first field! int a_field; }; struct NodeB { struct Node; // base class, first field! float b_field; }; void take_node(struct Node *node) // takes a generic pointer to the base-class { if ( node->type == OBJ_TYPE_A ) { struct NodeA *a_node = (NodeA)node; a_node->a_field = whatever; } else if ... ... } // until here that is normal C99 int main(void) { struct NodeA anode = { .type = OBJ_TYPE_A, .a_field = 42 }; struct NodeB bnode = { .type = OBJ_TYPE_B, .b_field = 4.2 }; take_node((Node *)&anode); // standard: inhibits type checking take_node(&anode); // plan9-extension: no cast required take_node(&bnode); // plan9-extension: no cast required }

Pro es que no hay necesidad de extender la estructura base (no depende de las estructuras secundarias) al crear nuevas estructuras secundarias. Las estructuras anónimas permiten crear elementos secundarios de los elementos secundarios directos y acceder a campos como cabría esperar en OOP (sin cadena de especificadores de campo: child1_1_1_ptr->child1_1.child1.base.base_field , pero solo child1_1_1_ptr->base_field ).

Las últimas dos invocaciones de take_node usan la extensión C gcc -fplan9-extensions . Esto evita convertir a la clase base mientras aún habilita la verificación de tipo (clase base o un niño). Este es un gran paso hacia OOP ya.

Eso se puede extender a un enfoque OOP de tamaño completo, incluidos los métodos virtuales. Sin embargo, hay un punto en el que usar un verdadero OOPL como C++ se vuelve más fácil.

over 4 years ago · Santiago Trujillo Denunciar

0

C no contiene ninguna información de tiempo de ejecución sobre lo que apunta un puntero. Puede crear una estructura que contenga un campo de tipo y una unión que contenga cualquier otra cosa que desee almacenar.

 enum node_type { NODE_TYPE_STRING, NODE_TYPE_INT, NODE_TYPE_DOUBLE, NODE_TYPE_OTHER_STRUCT }; struct other_struct { // define some fields }; struct node_data { enum node_type type; union { char *string; int i; double d; struct other_struct other; } data; };
over 4 years ago · Santiago Trujillo Denunciar

0

C es un lenguaje compilado. La información sobre el "tipo" de una estructura o cualquier otra variable solo existe en tiempo de compilación, no en tiempo de ejecución. Si necesita polimorfismo, debe implementarlo usted mismo.

Un método común es convertir el primer elemento de un conjunto de estructuras en un identificador. Ya sea un número (quizás un índice en una tabla de información de tipo), o algo así como la dirección de una estructura de información de tipo. Luego puede asignar un puntero a cualquiera de esas estructuras y verificar ese primer campo para decidir qué hacer con él.

over 4 years ago · Santiago Trujillo Denunciar
Responde la pregunta
Encuentra empleos remotos

¡Descubre la nueva forma de encontrar empleo!

Top de empleos
Top categorías de empleo
Empresas
Publicar vacante Precios Comercial
Legal
Términos y condiciones Política de privacidad
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomiéndame algunas ofertas
Necesito ayuda