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


 


Tema destacado:


+  Foro de elhacker.net
|-+  Programación
| |-+  Programación C/C++ (Moderadores: Eternal Idol, Littlehorse)
| | |-+  [Source] Split en C++ 100% funcional
0 Usuarios y 1 Visitante están viendo este tema.
Páginas: [1] Ir Abajo Respuesta Imprimir
Autor Tema: [Source] Split en C++ 100% funcional  (Leído 12,310 veces)
~~
Ex-Staff
*
Desconectado Desconectado

Mensajes: 2.982


Ver Perfil WWW
[Source] Split en C++ 100% funcional
« en: 4 Enero 2007, 21:33 »

Hola:

Aki os dejo como aporte la funcion Split para C++. Esta funcion imita a la de VB y vale para obtener un trozo de cadena separandola por un carater determinado. Lo mejor es q la proveis vosotros mismos:

Código:
#include <iostream>
#include <string>

std::string Split(std::string cadena, char m, int numero);

int cuenta; //Determina el espacio del Buffer en el q escribimos
int posicion; //Determina la posición del caracter por donde keremos partir

int main()
{
std::string entrada;
char caracter;
int numero;

std::cout << "Introduzca la cadena   --> ";
std::cin >> entrada;

std::cout << "Introduzca el caracter --> ";
std::cin >> caracter;

std::cout << "Introduzca el numero   --> ";
std::cin >> numero;

std::string Recibido;
Recibido = Split(entrada,caracter, numero);

std::cout << Recibido;

return 0;
}

std::string Split (std::string cadena, char m, int numero)
{
posicion = cadena.find (m);

if (posicion != -1) //Si se encuentra el caracter deseado
{
std::string principal  (cadena.substr (0,posicion)); //Guardamos el primer trozo de cadena
std::string secundaria (cadena.substr (posicion + 1,cadena.length ())); //Guardamos el resto de la cadena

if (cuenta == numero)
{
std::string Cadena;
Cadena =  principal;
return Cadena;
}

cuenta++;
Split (secundaria,m,numero);
 
}else{
return cadena; //Si no encontramos el caracter deseado devolvemos la cadena entera
}


}

Espero q os sea util por q sus kebraderos de cabeza me a costado, aunke luego la solucion era facil xDD

1S4ludo y gracias a los q por lo menos me han intentado ayudar ;)


« Última modificación: 9 Septiembre 2009, 23:53 por E0N » En línea

~~
Ex-Staff
*
Desconectado Desconectado

Mensajes: 2.982


Ver Perfil WWW
Re: [Aportación] Split 99% funcional, alguien me ayuda con ese 1%?
« Respuesta #1 en: 5 Enero 2007, 12:53 »

Aclaro un poco la parte q no me sale por q parece q no se entiende. Pretendo hacer ersto:

Código:
#include <iostream>
#include <string>

std::string *Split(std::string cadena, char m);

std::string Buffer [250];//El Buffer de cadenas
int cuenta; //Determina el espacio del Buffer en el q escribimos
int posicion; //Determina la posición del caracter por donde keremos partir

int main()
{
std::string entrada;
char caracter;

std::cout << "Introduzca la cadena --> ";
std::cin >> entrada;

std::cout << "Introduzca el caracter --> ";
std::cin >> caracter;

//Si intentamos mostrar el resultado de cualkiera de estas dos maneras aparecen simbolos raros ¿?¿?
std::string* devuelta = Split (entrada,caracter);
std::cout << *devuelta << '\n';

std::cout << *Split(entrada,caracter) << '\n';

return 0;
}

std::string *Split (std::string cadena, char m)
{
posicion = cadena.find (m);

if (posicion != -1) //Si se encuentra el caracter deseado
{
std::string principal  (cadena.substr (0,posicion)); //Guardamos el primer trozo de cadena
std::string secundaria (cadena.substr (posicion + 1,cadena.length ())); //Guardamos el resto de la cadena

Buffer [cuenta] =  principal;
cuenta++;

Split (secundaria,m);

}else{ //Si no se encuentra salimos
Buffer[cuenta] = cadena;
static std::string *Retorno = new std::string[cuenta+2]; //Creamos una matriz con lo espacios justos q keremos debolver

for (int h=0; h <= cuenta; h++) //Asignamos los valores q nos interesan
{
Retorno[h] = Buffer[h];
}
cuenta = 0; //Ponemos la cuenta a cero para porder seguir usando la función
std::cout << "La cadena bien devuelta seria: " << Retorno[0] << '\n';//Aki vemos como lo q se va a devolver es correcto
return &Retorno[0];
}

}

Si ponemos en la entrada "Hola|mundo" y q lo parta por el '|' nos deberia devolver:
devuelta[0] = Hola
devuelta[1] = mundo
Pero no lo hace, lo curioso es q si pongo "Hola" y busco '|' por ejemplo, evidentemente no lo encuentra y lo curioso es q me devuelve todo bien ¿??¿? y estoy usando metodos de devolucion q con una matriz de enteros por ejemplo funcionan bien... q raro no??

Os pongo dos salidas de consola para q veais al lo q me refiero:

Para q encuentre el caracter deseado:
Citar
Introduzca la cadena --> Hola|mundo
Introduzca el caracter --> |
La cadena bien devuelta seria: Hola
âPÞQ·  âj
èUÓRâý►ï╠ëeðìEõPÞÊ·  ëE└Þz·  â─¶ëE╝ïM╝Qh╚èG
La cadena bien devuelta seria: Hola
└ ↕
Simbolos raros  :-(

Pero si ponemos para q no encuentre en caracter deseado:
Citar
Introduzca la cadena --> Hola|mundo
Introduzca el caracter --> 1
La cadena bien devuelta seria: Hola|mundo
Hola|mundo
La cadena bien devuelta seria: Hola|mundo
Hola|mundo
Lo devuelve perfewctamente  :huh: :huh: :huh:

Alguien sabe por q puede ser??


En línea

clascrip

Desconectado Desconectado

Mensajes: 9


Ver Perfil
Re: [Aportación] Split 99% funcional, alguien me ayuda con ese 1%?
« Respuesta #2 en: 8 Enero 2007, 20:34 »

Hola EON, el fallo esta en que la direccion de la matriz dinámica se pierde por el camino  ;D.

En en else, haces un

Código:
return &Retorno[0];

pero si la función se había llamada alguna vez a sí misma, después de esta llamada vas a parar a:

Código:
Split (secundaria,m);

Si te fijas en esta parte del código, no guardas la dirección que devuelve la función en ninguna variable y al finalizar todas las llamadas que se ha hecho la función a sí misma, la función no devuelve nada.

Para solucionarlo puedes declarar el puntero Retorno al principio de la función y asignarle NULL. Además tendrías que guardar en Retorno el resultado de la llamada a:

Código:
Split (secundaria,m);

Y has de poner la sentencia:

Código:
return &Retorno[0];

fuera del else.

Aparte de esto, algunos detalles más:

Esto:

Código:
return &Retorno[0];

Equivale a:

Código:
return Retorno;

Código:
static std::string *Retorno = new std::string[cuenta+2];

No entiendo porque lo pones como static ni porque pones cuenta + 2. Yo creo que no hace falta el static y que solo tienes que poner cuenta + 1 (porque el primer indice es el 0, en vez del 1 y entonces hay un elemento más que el número del último indice).

Aparte de eso, reservas memoria con new pero no la liberas, antes del return 0 deberías liberar la memoria que has reservado. Lo puedes hacer asi:

Código:
delete devuelta;

Por ultimo, con esto:

Código:
std::cout << *devuelta << '\n';

Solo muestras la primera subcadena, para mostrarlas todas tendrías que saber cuantas subcadenas hay y utilizar un bucle:

Código:
for(int i = 0; i < n; i++) {
        std::cout << devuelta[i]<< '\n';
}

Donde n es el número de subcadenas.

Bueno, espero haberme explicado.
Saludos.
En línea

Rozor

Desconectado Desconectado

Mensajes: 269


As I Walk Through The Valley Of The Shadow Of Dead


Ver Perfil WWW
Re: [Aportación] Split 99% funcional, alguien me ayuda con ese 1%?
« Respuesta #3 en: 9 Enero 2007, 14:20 »

Ami me funciona bien compilado en Visual Studio 6.0 SP6 , en modo Debug o Release

Código:
Introduzca la cadena --> hola|mundo
Introduzca el caracter --> 1
hola|mundo
Press any key to continue
En línea

out in the streets they call it murder....
~~
Ex-Staff
*
Desconectado Desconectado

Mensajes: 2.982


Ver Perfil WWW
Re: [Aportación] Split 99% funcional, alguien me ayuda con ese 1%?
« Respuesta #4 en: 10 Enero 2007, 16:52 »

Citar
Ami me funciona bien compilado en Visual Studio 6.0 SP6 , en modo Debug o Release

Código:
Introduzca la cadena --> hola|mundo
Introduzca el caracter --> 1
hola|mundo
Press any key to continue

Si te devuelve eso es q no funciona bien xDD Tendria q ponerte:

Código:
Introduzca la cadena --> hola|mundo
Introduzca el caracter --> |
hola

Ya puse arriba q si no encontraba el caracter (como pone en tu ej) funcionaba bien.

Hola EON, el fallo esta en que la direccion de la matriz dinámica se pierde por el camino  ;D.

En en else, haces un

Código:
return &Retorno[0];

pero si la función se había llamada alguna vez a sí misma, después de esta llamada vas a parar a:

Código:
Split (secundaria,m);

Si te fijas en esta parte del código, no guardas la dirección que devuelve la función en ninguna variable y al finalizar todas las llamadas que se ha hecho la función a sí misma, la función no devuelve nada.

Para solucionarlo puedes declarar el puntero Retorno al principio de la función y asignarle NULL. Además tendrías que guardar en Retorno el resultado de la llamada a:

Código:
Split (secundaria,m);

Y has de poner la sentencia:

Código:
return &Retorno[0];

fuera del else.

No se pierde por el camino, ya q la voy guardando en el Buffer, q es externo a la funcion.


Citar
Código:
return &Retorno[0];

Equivale a:

Código:
return Retorno;

Lo se pero me gusta mas usar la de arriba, por q representa mejor el caracter matricial.


Citar
Código:
static std::string *Retorno = new std::string[cuenta+2];

No entiendo porque lo pones como static ni porque pones cuenta + 2. Yo creo que no hace falta el static y que solo tienes que poner cuenta + 1 (porque el primer indice es el 0, en vez del 1 y entonces hay un elemento más que el número del último indice)

Ahí tienes razon ;) pero como ya no me funcionaba keria provar todas las posibilidades antes de preguntar, a ver si era por eso y al final lo posteé asi xDD

Citar
Aparte de eso, reservas memoria con new pero no la liberas, antes del return 0 deberías liberar la memoria que has reservado. Lo puedes hacer asi:

Código:
delete devuelta;

Sip, pero es q si la borro no la devolveria no??

Por ultimo, con esto:

Código:

std::cout << *devuelta << '\n';


Solo muestras la primera subcadena, para mostrarlas todas tendrías que saber cuantas subcadenas hay y utilizar un bucle:

Código:

for(int i = 0; i < n; i++) {
        std::cout << devuelta<< '\n';
}


Donde n es el número de subcadenas.

Bueno, espero haberme explicado.
Saludos.

Ya, era solo para provar q devolvia bien y ya ni el primero devuelve bien...



Weno q al final ya se como hacerlo funcionar xDD solo hay q añadir un parametro mas por ej Split ("Cadena|a|partir,'|',0) asi no devolveria cadna q es la primera de las partes (de ahí el 0) asi es facil llamarse solamete las veces necesarias y q devuelva lo q interesa, pero de todas formas gracias por la ayuda ;)

1S4ludo
En línea

clascrip

Desconectado Desconectado

Mensajes: 9


Ver Perfil
Re: [Aportación] Split 99% funcional, alguien me ayuda con ese 1%?
« Respuesta #5 en: 10 Enero 2007, 19:50 »

Mira te pongo el código con las correciones que hice a ver que te parece:

Código:
#include <iostream>
#include <string>

std::string *Split(std::string cadena, char m);

std::string Buffer [250];//El Buffer de cadenas
int cuenta; //Determina el espacio del Buffer en el q escribimos
int posicion; //Determina la posición del caracter por donde keremos partir

int main()
{
std::string entrada;
char caracter;

std::cout << "Introduzca la cadena --> ";
std::cin >> entrada;

std::cout << "Introduzca el caracter --> ";
std::cin >> caracter;

std::string* devuelta =  Split (entrada,caracter);

delete devuelta;

return 0;
}

std::string *Split (std::string cadena, char m)
{
posicion = cadena.find (m);
std::string *Retorno = NULL;

if (posicion != -1) //Si se encuentra el caracter deseado
{
std::string principal  (cadena.substr (0,posicion)); //Guardamos el primer trozo de cadena
std::string secundaria (cadena.substr (posicion + 1,cadena.length ())); //Guardamos el resto de la cadena

Buffer [cuenta] =  principal;
cuenta++;

Retorno = Split (secundaria,m);

}else {
          Buffer[cuenta] = cadena;
         
          Retorno = new std::string[cuenta+1]; //Creamos una matriz con lo espacios justos q keremos debolver
         
          for (int h=0; h <= cuenta; h++) //Asignamos los valores q nos interesan
{
Retorno[h] = Buffer[h];
std::cout << Retorno[h] << '\n';
}
cuenta = 0;
    }
    return Retorno;

}


PD: Más vale un código que mil explicaciones  ;D.
En línea

~~
Ex-Staff
*
Desconectado Desconectado

Mensajes: 2.982


Ver Perfil WWW
Re: [Aportación] Split 99% funcional, alguien me ayuda con ese 1%?
« Respuesta #6 en: 14 Enero 2007, 12:16 »

Pues a mi no me funciona clascrip... en medio de la ejecucion me sale un error de esos de q a sucedido un problema bla, bla bla...

Mirad e creado este q deberia funcionar pero de nuevo no devuelve bien, a ver si le veis el fallo:

EDITADO: Ver el de abajo
« Última modificación: 14 Enero 2007, 17:26 por E0N » En línea

~~
Ex-Staff
*
Desconectado Desconectado

Mensajes: 2.982


Ver Perfil WWW
Re: [Aportación] Split 99% funcional, alguien me ayuda con ese 1%?
« Respuesta #7 en: 14 Enero 2007, 17:25 »

Hola de nuevo ;)

A ver el code de antes es un poco lioso y no es necesario, este es el weno:

Código:
#include <iostream>
#include <string>

std::string Split(std::string cadena, char m, int numero);

std::string Buffer [250];//El Buffer de cadenas
int cuenta; //Determina el espacio del Buffer en el q escribimos
int posicion; //Determina la posición del caracter por donde keremos partir

int main()
{
std::string entrada;
char caracter;
int numero;

std::cout << "Introduzca la cadena   --> ";
std::cin >> entrada;

std::cout << "Introduzca el caracter --> ";
std::cin >> caracter;

std::cout << "Introduzca el numero   --> ";
std::cin >> numero;

std::string Recibido;
Recibido = Split(entrada,caracter, numero);

std::cout << Recibido;

return 0;
}

std::string Split (std::string cadena, char m, int numero)
{
posicion = cadena.find (m);

if (posicion != -1) //Si se encuentra el caracter deseado
{
std::string principal  (cadena.substr (0,posicion)); //Guardamos el primer trozo de cadena
std::string secundaria (cadena.substr (posicion + 1,cadena.length ())); //Guardamos el resto de la cadena

Buffer [cuenta] =  principal;
cuenta++;

Split (secundaria,m,numero);

}else{ //Si no se encuentra salimos
Buffer[cuenta] = cadena;

std::string Cadena;
Cadena = Buffer[numero];
std::cout << Cadena << '\n'; //Vemos como deberia devolver bien


return Cadena;
}

}


Sin embargo al ejecutar el programa me salta un error de esos de q se a de cerrar y si quiero enviar los errores...
Si le doi al debug me aparece "Unhandled exception in Split.exe: 0xC0000005: Acces Violation" Alguien sabe por q sucede esto o por lo menos q sucede??

Gracias ;)
1S4ludo
En línea

~~
Ex-Staff
*
Desconectado Desconectado

Mensajes: 2.982


Ver Perfil WWW
Re: [Aportación] Split 99% funcional, alguien me ayuda con ese 1%?
« Respuesta #8 en: 14 Enero 2007, 17:37 »

Vale, me siento estupido contestndome a mi mismo... al final era mas facil de lo q creia, ya tengo la funcion, esta en el primer post

1S4ludo
En línea

Páginas: [1] Ir Arriba Respuesta Imprimir 

Ir a:  

Mensajes similares
Asunto Iniciado por Respuestas Vistas Último mensaje
[SOURCE] MultiSplit7913 Un split diferente XD « 1 2 »
Programación Visual Basic
79137913 14 2,275 Último mensaje 22 Marzo 2011, 19:09
por Psyke1
SetWindowsHookEx ¿hay un ejemplo claro y funcional?
Programación C/C++
yovaninu 3 3,852 Último mensaje 6 Agosto 2011, 05:39
por naderST
Descargar un SWF y funcional en PC offline, posible?
Multimedia
Tefaa 2 2,733 Último mensaje 22 Enero 2013, 12:49
por adrianmendezRap
Programación funcional
Programación General
csp 5 1,405 Último mensaje 30 Octubre 2013, 01:03
por El Benjo
Programación funcional
Programación General
FermatsTheorem 2 583 Último mensaje 10 Mayo 2017, 23:05
por ivancea96
Aviso Legal - Powered by SMF 1.1.21 | SMF © 2006-2008, Simple Machines