[C con Clase] otro error mysql-c

Steven Davidson steven en conclase.net
Mie Jun 13 19:31:50 CEST 2007


Hola Duna,

El pasado 2007-06-13 10:53:12, Duna escribió:

D> Hola.
D> No sé qué me pasa, pero estoy teniendo muchos problemas con la conexión
D> entre estructuras en c y asociar los datos que obtengo de la base de datos
D> mysql.
D> os pongo el código y el error a ver si alguie me puede ayudar, ya que se lo
D> agradecería muchiiiiiiiiiisimo...

Veamos la parte que interesa.

D> struct final_l_titulo
D> {
D>         char* titulo;
D>         struct final_l_titulo * next;
D> };

[CORTE]

D>                  if((res1 = mysql_store_result(base)))
D>                  {
D>                         i = (int) mysql_num_rows(res1);
D>                         j = (int) mysql_num_fields(res1);
D>                         printf ("\nEl número de resultados es: %d\n", i);
D>                         columna = mysql_fetch_fields(res1);
D>                         if (i!=0)
D>                         {
D>                         primero=NULL;
D>                         anterior=NULL;
D>                         for(l = 0; l < i; l++)
D>                         {
D>                                 consulta1= (final_l_titulo *)malloc (sizeof
D> (final_l_titulo));
D>                                 row = mysql_fetch_row(res1);
D>                                 lon = mysql_fetch_lengths(res1);
D>                                 printf ( "Registro no. %d", l+1);
D>                                 // Mostrar cada campo y su longitud:
D>                                 k=0;
D>                                 consulta1->titulo = row[k];        AQUI ES
D> DONDE ME DA EL ERROR

Esto es normal. Ten presente que el campo de 'titulo' es un puntero y 'row[]' también lo es. Esto significa que se copian las direcciones de memoria y no el contenido de la cadena. Lo que deberías hacer es crear memoria dinámicamente para 'titulo'. Por ejemplo,

consulta1->titulo = (char *) malloc( strlen(row[k])+1 );
strcpy( consulta1->titulo, row[k] );

Obviamente, tendrás que liberar la memoria de cada 'titulo' antes de liberar la memoria de cada nodo de la lista enlazada.

D>                                 printf ("\n%s", consulta1->titulo);
D>                                 printf (" ");
D>                                 k++;
D>                                 consulta1->next=NULL;
D>                                 if (primero == NULL)
D>                                         primero=consulta1;
D>                                 else
D>                                         anterior->next=consulta1;

Esto es un error, porque 'anterior' al comienzo es un puntero nulo. Aquí el sistema operativo te dará otro error. La solución es asignar el primer nodo a 'anterior' para que apunte a un nodo válido. Esto es,

if( !primero )
  primero = anterior = consulta1;
else
  anterior->next = consulta1;

anterior = consulta1;

D>                                 anterior=consulta1;
D>                         }
D>                         }
D>                  }



D>                  if (i != 0)
D>                  {
D>                         consulta1->next=NULL;
D>                         consulta1=primero;
D>                  }
D>                  if (i==0)
D>                  {
D>                          consulta1=NULL;
D>                  }

Primeramente, estas condiciones son mutuamente exclusivas y por tanto deberías expresarlas como 'if/else'. En segundo lugar, no estoy muy seguro de por qué quieres molestarte con 'consulta1'. Lo que realmente te interesa es el comienzo de la lista enlazada; es decir, el puntero 'primero'.

Si retornas 'primero', puedes eliminar todas estas condiciones.

D>                  //mysql_free_result(res1);

Debes liberar la memoria invocando esta función.

D>                  mysql_close(base);
D>                  return (consulta1);
D> }
D> y el error que me da cuando hago un debug es este:
D> Unhandled exception in proyecto.exe : 0x000000005 Access violation

Este error casi siempre se refiere a un problema de direcciones de memoria: punteros inválidos, memoria liberada pero usada posteriormente, etc..


Espero que todo esto te ayude.

Steven


Más información sobre la lista de distribución Cconclase