Foros del Web » Programación para mayores de 30 ;) » C/C++ »

explicacion logica recursividad??

Estas en el tema de explicacion logica recursividad?? en el foro de C/C++ en Foros del Web. hola amigos, estoy aprendiendo recursividad pero no le pillo la logica. Os pongo un ejemplo: unsigned sumanaturales( unsigned n ) { int suma; if( n>0 ...
  #1 (permalink)  
Antiguo 12/02/2011, 05:26
 
Fecha de Ingreso: noviembre-2007
Mensajes: 208
Antigüedad: 16 años, 5 meses
Puntos: 2
explicacion logica recursividad??

hola amigos, estoy aprendiendo recursividad pero no le pillo la logica. Os pongo un ejemplo:


unsigned sumanaturales( unsigned n )
{
int suma;

if( n>0 )
{
return suma = n + sumanaturales( n-1 );
}
else
{
suma = 0;
}


}

int main() {
int n,suma;

cout << "Introduce n: " << endl;
cin >> n;

suma = sumanaturales(n);
cout << "La suma es: " << suma;
return 0;
}

No entiendo porque hay que poner el else{suma=0} es algo que me ha dicho mi profesora pero no entiendo porque, y tampoco entiendo donde devuelve el control de flujo el programa ya que imaginaros cuando envia n=1 entonces enviaria un n=0 aqui: return suma = n + sumanaturales( n-1 );

por tanto no deberia volver a entrar en el if( n>0 ) y por tanto no deberia devolver el valor suma... nose estoy echo un lio haber si me podeis ayudar
  #2 (permalink)  
Antiguo 12/02/2011, 17:56
 
Fecha de Ingreso: junio-2010
Mensajes: 46
Antigüedad: 13 años, 9 meses
Puntos: 0
Respuesta: explicacion logica recursividad??

hola amigo.. voy a intentar explicarte espero saberlo hacer

una funcion recursiva es aquella que se llama asi misma de forma directa o indirecta (a travez de otra funcion)

metodologia:
* una funcion recursiva sabe unicamente como resolver el caso mas sencillo o caso base.
* si se llama a una funcion con un problema mas complejo, esta divide la tarea en dos piezas conceptuales:

1. la pieza que sabe resolver el caso base o problema mas simple.
2. la pieza que no sabe como resolver el problema..

para que la recursividad se de la pieza 2 debe llamar a un problema (funcion) similar al original pero una vesion mas simple de esta (mas facil de resolver).

* como la pieza 2 representa una version similar al problema original, esta va llamar (cuantas veces sea necesario) a una nueva copia del problema cada vez mas pequeño o simple (la funcion se llama asi misma). a esto se le conoce como paso recursivo

* para que la recursividad acabe, esta serie de problemas cada vez mas pequeños o mas sencillos debe converger en el caso baso. cuando sucede esto la funcion ya sabe como resolver el problema y en este punto se genera una serie de retornos hasta llegar a la funcion original y devuelve el resultado final a la funcion que la llamo (por lo general main()).
Código:
                   llamadas                                                              Retornos
funcion original->  *                                                                       * <- funcion origi
                             |                                                                       ^
                             *                                                                       *
                             |                                                                       ^
                             *                                                                       *
                             |                                                                       ^
caso base ->        *                                                                        * <- caso base
por lo general las funciones recursivas tienen una estructura similar a esto

Código:
void funcionRecursiva (<tipo>valor)
{
   if (evaluacion) // evalua el caso base      ---> pieza 1
   return 1; // (por ejemplo) caso base.
  else //paso recursivo
  return valor*funcionRecursiva (valor-1); // observa que el problema se hace mas sencillo (valor-1)
}
te pongo un ejemplo (elevar un numero a una potencia)
Código:
//Ejercicio de Recursividad.
# include <iostream>

using namespace std;
long int potencia (int,int);
int main ()
{
    int base,exponente;
    cout<<"\n\t programa Potencia";
    cout<<"\n escriba el numero a elevar: \n";
    cin>>base;
    cout<<" elevado a ";
    cin>>exponente;
    cout<<"\n Resultado: "<<potencia(base,exponente);
    return 0;
}

long int potencia (int b, int e)
{
    if (e==1) //pieza 1
    {
        return b; //caso base
    }
    else //pieza 2
    {
        return b*potencia(b,e-1); //paso recursivo
    }
}
  #3 (permalink)  
Antiguo 13/02/2011, 16:39
 
Fecha de Ingreso: noviembre-2007
Mensajes: 208
Antigüedad: 16 años, 5 meses
Puntos: 2
Respuesta: explicacion logica recursividad??

hola,

Te agradezco muchisimo tu respuesta.

Pero ami lo que no me queda claro es la logica de trabajo de la recursividad, ya que yo uso la logica del funcionamiento de las funciones y la aplico tambien para la recursividad pero esta claro que no es la misma.

Me gustaria que en el ejemplo que tu me has puesto me tracearas un poco que es lo que hace el programa:

Cita:
long int potencia (int b, int e)
{
if (e==1) //pieza 1
{
return b; //caso base
}
else //pieza 2
{
return b*potencia(b,e-1); //paso recursivo
}
}
por ejemplo b= 3 elevado a 4 (e==4). No entra en el if, se va al else y hace la potencia, ahora vuelve a llamarse a si misma y ahora e==3. Donde va el flujo de control del programa? vuelve a mirar si puede entrar al if y sino entra en el else y vuelve a repetir la operacion? y una vez que e==1 entonces entraria en el if y devolveria 'b' y entonces ya no devolveria el valor del else no?

esque lo que no entiendo son los pasos que hace la recursividad para resolver el problema porque yo lo veo todo como si fuera una funcion pero esta claro que no funciona como tal. La teoria mas o menos si que la tengo clara.

un saludo y gracias de nuevo por tu respuesta
  #4 (permalink)  
Antiguo 13/02/2011, 17:07
 
Fecha de Ingreso: abril-2010
Ubicación: Rosario
Mensajes: 1.850
Antigüedad: 14 años
Puntos: 228
Respuesta: explicacion logica recursividad??

La recursividad si responde a la logica de las funciones. Pero que pasa, cada vez que haces un llamado a la funcion se crean en memorias nuevas variables locales y argumentos.

En ese ejemplo de potencia, supone que llamamos asi:
potencia(4,3);

En el primer llamado a la funcion e no es igual a uno por lo que el if pasa al else. Ahi se va a calcular 4 * potencia(4,3-1); Para calcular ese numero, se realiza un nuevo llamado a la funcion potencia que es totalmente aparte del anterior. Ahora los argumentos esta vez son 4 y 2.

De nuevo e no es igual a uno, por lo que se re quiere calcular 4 * potencia(4,1). Se hace un llamado nuevamente a potencia, completamente distitno a los otros dos, y ahora si e es igual a uno por lo que se devuelve 4.

En el segundo llamado tenias que calcuar 4 * potencia(4,1) = 4 * 4 = 16. Entonces devolvemos 16. Y llegamos al primner llamado en donde debiamos calcular
4 * potencia(4,2) = 4 * 16 = 64
Y ese es el resultado de la funcion.

Un desarrollo mas matemtico seria:

potencia(4,3) = 4 * potencia(4,2) = 4 * 4 * potencia(4,1) = 4 * 4 * 4 = 4 * 16 = 64
  #5 (permalink)  
Antiguo 14/02/2011, 04:51
 
Fecha de Ingreso: noviembre-2007
Mensajes: 208
Antigüedad: 16 años, 5 meses
Puntos: 2
Respuesta: explicacion logica recursividad??

hola,

Muchas gracias por la aclaracion.

Pero y entonces para que sirve el caso base? he comprobado que si se quita la recursividad funciona igual
  #6 (permalink)  
Antiguo 14/02/2011, 07:26
 
Fecha de Ingreso: abril-2010
Ubicación: Rosario
Mensajes: 1.850
Antigüedad: 14 años
Puntos: 228
Respuesta: explicacion logica recursividad??

El caso base sirve para que no se llame constantemente a la funcion. En algun momento debe parar el llamado recursivo. Lo mismo pasa en la induccion matematica.

Proba esta funcion asi:

Código C++:
Ver original
  1. long int potencia (int b, int e)
  2. {
  3. return b*potencia(b,e-1); //paso recursivo
  4. }

Eso si como esta no va a parar nunca. Y como hiciste para quitarle la recursividad?? Pone la funcion que segun vos sigue funcionando.
  #7 (permalink)  
Antiguo 14/02/2011, 11:12
 
Fecha de Ingreso: junio-2010
Mensajes: 46
Antigüedad: 13 años, 9 meses
Puntos: 0
Respuesta: explicacion logica recursividad??

hola BoKeRoN18.. sam90 te lo explico correctamente.. el caso base sirve para evitar la recursion infinita..

la funcion "piensa asi".. si exponente es igual a 1 entonces no tengo que hacer nada solo devuelvo la base porque a^1=a. sino entonces multiplica la base por la base^e-1 porque es lo mismo tener 3^3 que tener 3*3^2 o 3*3*3^1...

osea si tienes base=2 y exponente =3. la funcion no entra en el if porque la evaluacion es falsa ya que exponente no es igual a 1. entonces va a multiplicar 2*2^2.. luego 2*2*2^1 y en este caso la funcion reconoce el caso base y devuelve 2.. apartir de aqui se producen una serie de retornos.. la ultima funcion llamada devuelve 2, la que le sigue devuelve 2*2 y la primera (la original) devuelve a main 2*2*2.

espero me entiendas sino pregunta
  #8 (permalink)  
Antiguo 15/02/2011, 18:36
 
Fecha de Ingreso: enero-2011
Mensajes: 25
Antigüedad: 13 años, 2 meses
Puntos: 1
Respuesta: explicacion logica recursividad??

Podrás encontrar información [URL="http://www.scenebeta.com/tutorial/recursividad"]aquí[/URL]
  #9 (permalink)  
Antiguo 16/02/2011, 13:01
 
Fecha de Ingreso: noviembre-2007
Mensajes: 208
Antigüedad: 16 años, 5 meses
Puntos: 2
Respuesta: explicacion logica recursividad??

hola muchachos gracias por vuestras explicaciones pero creo que me he perdido un poco mas :S

long int potencia (int b, int e)
{
if (e==1) //pieza 1
{
return b; //caso base
}
else //pieza 2
{
return b*potencia(b,e-1); //paso recursivo
}
}

Voy a tracear un ejemplo:

si e ==3 y b==2
1- entra en el else hace 2*potencia(2,3-1) // pero aqui no devuelve todavia verdad??
2 - rapidamente vuelve al principio de la funcion y ve que todavia no puede entrar a la condicion if por lo que va al else y alli vuelve: return 2*potencia(2,2-1);
3 - ahora vuelve a llamar a la funcion y ahora si entra en el if e==1 y devuelve b y aqui se termina la funcion.

Preguntas si el valor de 'b' no se ha ido acumulando en ningun sitio como devuelve b en el if? porque se supone que en else no llega nunca a devolver ningun valor no? y si es asi donde se acumulan?

nose cada vez me lio mas :S:S:S::S
  #10 (permalink)  
Antiguo 16/02/2011, 13:31
 
Fecha de Ingreso: abril-2010
Ubicación: Rosario
Mensajes: 1.850
Antigüedad: 14 años
Puntos: 228
Respuesta: explicacion logica recursividad??

Si en el main llamas a una funcion cualquiera, y desde ella pones un return, vas volves al main.
Ahora si desde una funcion f llamas a la funcion f nuevamente, al poner un return desde la funcion f vas a volver a la funcon f pero desde donde fue llamado.

Para entender un poco mejor eso te recomiendo que imprimas en pantalla y vas a poder seguir la ruta:

Código C++:
Ver original
  1. long int potencia (int b, int e)
  2. {
  3.      long int temporal;    
  4.      cout << e;
  5.     if (e==1) //pieza 1
  6.     {
  7.         return b; //caso base
  8.     }
  9.     else //pieza 2
  10.     {
  11.               cout << "llamo a potencia con" << b << " y " << e -1;
  12.               temporal = potencia(b,e-1);    
  13.               return b*temporal; //paso recursivo
  14.     }
  15. }

Fijate si podes entender mejor como funcionan los llamados.
  #11 (permalink)  
Antiguo 16/02/2011, 16:47
 
Fecha de Ingreso: noviembre-2007
Mensajes: 208
Antigüedad: 16 años, 5 meses
Puntos: 2
Respuesta: explicacion logica recursividad??

pfff pero si esque entiendo que el 'e' se va reduciendo uno y lo de la base si eso si lo pillo pero esque no se como funciona la recursividad yo se que una funcion sirve para realizar un problema, que tu le pasas parametros y te devuelve algo si quieres, pero la recursividad no entiendo como va porque para empezar:

return b*potencia(b,e-1);

aqui por ejemplo donde se guarda el resultado del b que se esta multiplicando?? yo lo que he aprendido de programacion cuando tu haces una operacion lo guardas en una variable.. aqui como se guarda en b?? y otra cosa el return del if no se usa nunca no? cuando realmente devuelve la funcion es en el caso base no?

Yo creo que hasta que no vea un ejemplo no lo voy a comprender :S

Muchas gracias a todos por vuestra ayuda
  #12 (permalink)  
Antiguo 16/02/2011, 19:03
 
Fecha de Ingreso: abril-2010
Ubicación: Rosario
Mensajes: 1.850
Antigüedad: 14 años
Puntos: 228
Respuesta: explicacion logica recursividad??

Ya no se como explicartelo. Los dos return son alcanzados. Cada uno en diferentes llamadas al a funcion potencia.

Lo que no estas entendiendo es que cuando volves a llamar a la funcion potencia, osea haces el llamado recursivo, todas las variables locales y todo el entorno de la funcion es duplicado y se crea un nuevo llamado, preservando en memoria el anterior. Asi que cuando este nuevo llamado hace el return, osea, vuelve el valor, este llega al primer llamado de la funcion se realizan las cuentas y se vuevle a retornar un valor mas actualizado.
  #13 (permalink)  
Antiguo 17/02/2011, 13:19
 
Fecha de Ingreso: noviembre-2007
Mensajes: 208
Antigüedad: 16 años, 5 meses
Puntos: 2
Respuesta: explicacion logica recursividad??

hola, Siento mucho minar vuestra paciencia xd

Ya mas o menos lo voy entendiendo, cuando se hace el caso base entonces es cuando se empieza ha hacer las operaciones del resto de llamadas no?

empiezan a devolverse valores del resto de llamadas y finalmente se devuelve el valor no es asi?
  #14 (permalink)  
Antiguo 18/02/2011, 15:09
 
Fecha de Ingreso: febrero-2011
Mensajes: 1
Antigüedad: 13 años, 2 meses
Puntos: 0
Respuesta: explicacion logica recursividad??

Creo que el problema esta en entender como funciona el registro de activación (RA) y el paso de parametros reales a parametros formales.
En este caso concreto, suponiendo que le demos a la base el valor 2 y exponente 3. Cuando tu das los parametros (reales) en el main ( ) estos quedan almacenados en el registro de activacion del main durante todo el proceso como b==2 y e==3 . En canvio en la función potencia ocurre otra cosa:


1- El if no se ejecuta ya que e!=1 por lo que se la salta y se ejecutan las instrucciones del else con los
parametros reales que se le pasan desde el main ( ) b==2 y e== 3.
La funcion potencia crea su propio RA en el que b ==2*2 y e==2.

2- Como sigue sin cumplirse el if se vuelve a ejecutar el else pero esta vez los parmetros reales que se
le pasan a potencia son b=2*2 e==2 y despues se destruye el RA de la función.
Ahora el nuevo RA de potencia valdra b=2*2*2 y e==1.
3- Ahora el if se cumple y el preprocesador le devuelve el control al main ( ) con el valor b==6.


Si no me equivoco el tema funciona así. Espero que te sirva de ayuda.

Etiquetas: logica, recursividad
Atención: Estás leyendo un tema que no tiene actividad desde hace más de 6 MESES, te recomendamos abrir un Nuevo tema en lugar de responder al actual.
Respuesta




La zona horaria es GMT -6. Ahora son las 01:22.