elhacker.net cabecera Bienvenido(a), Visitante. Por favor Ingresar o Registrarse
¿Perdiste tu email de activación?.

 

 


Tema destacado: Rompecabezas de Bitcoin, Medio millón USD en premios


+  Foro de elhacker.net
|-+  Programación
| |-+  Programación C/C++ (Moderadores: Eternal Idol, Littlehorse, K-YreX)
| | |-+  [DUDA C] Dividir cadena en subcadenas (similar argv)
0 Usuarios y 1 Visitante están viendo este tema.
Páginas: [1] Ir Abajo Respuesta Imprimir
Autor Tema: [DUDA C] Dividir cadena en subcadenas (similar argv)  (Leído 7,506 veces)
setwarn

Desconectado Desconectado

Mensajes: 2


Ver Perfil
[DUDA C] Dividir cadena en subcadenas (similar argv)
« en: 6 Diciembre 2010, 14:42 pm »

Buenas a todos, es mi primer post aunque llevo tiempo leyendo y empapándome de la sabiduría que hay por aquí, asi que me he decidido lanzarme a preguntar, os cuento:

Estoy peleándome con los punteros, intento hacer una función (aunque de momento es un progama para no liarme) que haga algo similar a lo que devuelve argv, es decir, que divida una orden en varias cadenas, cada una apuntada por un puntero distinto para poderlas referenciar mediante los corchetes (Ej: orden[0],orden[1])

Quiero hacerlo para cualquier número de palabras, por lo que uso memoria dinámica, para dividir la orden uso strtok y su comportamiento es correcto, el problema lo tengo a la hora de manejar los punteros:
En **resul, voy reservando memoria con realloc para los punteros que apuntan a cada palabra, por tanto, mientras haya tokens hago lo siguiente:
- Aumento el tamaño de resul
- Reservo memoria para el puntero al token
- Le asigno el token

Código:
#include <string.h>
#include <stdio.h>
#include <stdlib.h>

int main(int argc, char *argv[]){
char linea[] = "send UDP 4500 50";
char **resul=NULL;
int numTokens,conta2;
char *sep=" ";//caracter separador de las ordenes
int conta=0;  //contador de número de tokens encontrados
char *saveptr,*token;

for(token=strtok_r(linea,sep,&saveptr); token!=NULL; token=strtok_r(NULL,sep,&saveptr)){
printf("token: %s\n",token);
printf("Tamaño: %i\n",(conta+1)*sizeof(char*));
resul = (char **)realloc(resul,(conta+1)*sizeof(char*)); //Aumentar tamaño para el array de punteros

resul[conta]= malloc(sizeof(char*)); //Reservar tamaño para el puntero
resul[conta]=token; //Asignar palabra al puntero
conta++;
}
//Imprimir resultados
for(conta2=0;conta2<conta;conta2++)
printf("resul: \"%s\"\n",resul[conta2]);
//Liberar memoria
for(conta2=0;conta2<conta;conta2++){
printf("liberando: %i\n",conta2);
free(resul[conta2]);
}
free(resul);
return(0);
}

La salida al ejecutarlo es:
Código:
$ ./lectura_consola 
token: send
Tamaño: 4
token: UDP
Tamaño: 8
token: 4500
Tamaño: 12
token: 50
Tamaño: 16
resul: "send"
resul: "UDP"
resul: "4500"
resul: "50"
liberando: 0
*** glibc detected *** ./lectura_consola: free(): invalid pointer: 0xbffb7f1b ***

Si lo arranco con valgrind para ver los fallos de memoria cuando va a hacer free(resul[0]) dice lo siguiente:
Código:
liberando: 0
==8372== Invalid free() / delete / delete[]
==8372==    at 0x40257ED: free (vg_replace_malloc.c:366)
==8372==    by 0x80489FA: main (lectura_consola.c:92)
==8372==  Address 0xbee8e28b is on thread 1's stack
Tal como está el código ahora mismo, guarda correctamente las palabras y las imprime bien, pero cuando voy a liberar memoria explota, al liberar resul[0] dice que no es un puntero válido. Tengo que haber cometido algún error con los punteros a la hora de manejarlos, pero llevo ya un par de tardes dándole vueltas y no consigo verlo.

Por otro lado al intentar pasar esto a una función, también me daba problemas, pero eso lo dejo para más adelante, de momento a ver si puedo arreglar esto con vuestra ayuda.


En línea

3mp3z@ndo

Desconectado Desconectado

Mensajes: 51


Ver Perfil
Re: [DUDA C] Dividir cadena en subcadenas (similar argv)
« Respuesta #1 en: 6 Diciembre 2010, 17:24 pm »

Bueno, yo todavia no me he metido con el tema de punteros y por ese lado no puedo ayudar,  pero al intentar compilar el código me daba warnings por pasarle demasiados argumentos a strtok, hice un par de retoques y en apariencia parece funcionar, aqui te dejo el codigo tal y como me funciona a mi:

Código
  1. #include <string.h>
  2. #include <stdio.h>
  3. #include <stdlib.h>
  4.  
  5. int main(int argc, char *argv[]){
  6. char linea[] = "send UDP 4500 50";
  7. char **resul=NULL;
  8. int numTokens,conta2;
  9. char *sep=" ";//caracter separador de las ordenes
  10. int conta=0;  //contador de número de tokens encontrados
  11. char *token;
  12.  
  13. for(token=strtok(linea,sep); token!=NULL; token=strtok(NULL,sep)){
  14. printf("token: %s\n",token);
  15. printf("Tamaño: %i\n",(conta+1)*sizeof(char*));
  16. resul = (char **)realloc(resul,(conta+1)*sizeof(char*)); //Aumentar tamaño para el array de punteros
  17.  
  18. resul[conta]= malloc(sizeof(char*)); //Reservar tamaño para el puntero
  19. resul[conta]=token; //Asignar palabra al puntero
  20. conta++;
  21. }
  22. //Imprimir resultados
  23. for(conta2=0;conta2<conta;conta2++)
  24. printf("resul: \"%s\"\n",resul[conta2]);
  25. //Liberar memoria
  26. for(conta2=0;conta2<conta;conta2++){
  27. printf("liberando: %i\n",conta2);
  28. free(resul[conta2]);
  29. }
  30. free(resul);
  31. return(0);
  32. }

Si te funciona, de lujo, si no seguro que pasa alguien por aqui y te aclara el tema de los punteros

Saludos


En línea

setwarn

Desconectado Desconectado

Mensajes: 2


Ver Perfil
Re: [DUDA C] Dividir cadena en subcadenas (similar argv)
« Respuesta #2 en: 6 Diciembre 2010, 18:01 pm »

Hola 3mp3z@ndo !

Me has hecho recordar una cosa que no dije en el primer post xD
Lo estoy haciendo bajo linux, misteriosamente en windows si funciona y no da ningún mensaje de error al liberar memoria, pero en linux (ubuntu concretamente) sigue dando el mismo error.

El strtok realmente me da igual usar strtok o strtok_r, había usado strtok_r porque leí que en caso de usar hilos hay que usar ese concretamente y como quería dejar el código para reusarlo...

Gracias de todas formas!
En línea

Páginas: [1] Ir Arriba Respuesta Imprimir 

Ir a:  

Mensajes similares
Asunto Iniciado por Respuestas Vistas Último mensaje
dividir cadena letra por letra
Scripting
morenochico 3 8,795 Último mensaje 3 Julio 2009, 18:46 pm
por leogtz
Duda con parámetros argc y argv
Programación C/C++
peternash 3 2,229 Último mensaje 11 Agosto 2013, 14:25 pm
por Eternal Idol
CREACION SUBCADENAS A PARTIR DE CADENA BINARIA
Programación C/C++
burnssss 3 2,664 Último mensaje 1 Noviembre 2013, 01:51 am
por rir3760
Dividir cadena en subcadena C++
Programación C/C++
gomezjuan 4 4,083 Último mensaje 18 Mayo 2020, 12:53 pm
por gomezjuan
alguna distro linux para dividir 4 escritorio en 1 pantalla similar a wndows 10,11?
GNU/Linux
bacanzito 1 3,785 Último mensaje 11 Marzo 2023, 22:03 pm
por B€T€B€
WAP2 - Aviso Legal - Powered by SMF 1.1.21 | SMF © 2006-2008, Simple Machines