2010-04-29 10 views
3

Pourquoi j'obtiens une erreur de segmentation dans ma fonction récursive. Il arrive chaque fois que je l'appelle quand une valeur supérieure à 4 en tant que paramètreErreur de segmentation C++ dans la fonction récursive

#include <iostream> 
#include <limits> 

using namespace std;  

int printSeries(int n){ 
    if(n==1){  
     return 1; 
    } 
    else if(n==2){  
     return 2; 
    } 
    else if(n==3){ 
     return 3; 
    } 
    else if(n==4){ 
     return printSeries(1) + printSeries(2) + printSeries(3); 
    } 
    else{  
     return printSeries(n-3) + printSeries((n-2) + printSeries(n-1)); 
    } 
} 


int main(){ 

     //double infinity = numeric_limits<double>::max(); 

     for(int i=1; i<=10; i++){ 
      cout << printSeries(i) << endl; 
     } 

    return 0; 

} 

Cela fonctionne très bien, mais je ne suis pas sûr que renvoie le résultat correct:

return printSeries(n-3) + printSeries(n-2) + printSeries(n-1); 
+0

Je remplace le premier cas de base par <= 1 mais je reçois toujours la segfault – user69514

+1

Ajoutez 'std :: cout << n << ',';' en haut de votre fonction 'printSeries()'. – sbi

Répondre

18
return printSeries(n-3) + printSeries((n-2) + printSeries(n-1)); 
//          ^^^^^^^^^^^^^^^^^^^^^^^^ 

incorrect l'imbrication de parenthèses provoque une récursion infinie, ce qui conduit à un débordement de pile (segfault).

Considérons lorsque n = 4,

f(4) = 1 + f(2 + f(3)) 
    = 1 + f(2 + 3) 
    = 1 + f(5) 
    = 1 + [ f(2) + f(3 + f(4)) ] 
    = ... 
+0

Ne devrait-il pas y avoir une exception? –

+1

@the_drow: Pourquoi devrait-il lancer une exception? – kennytm

+2

@the_drow: Pourquoi? C'est parfaitement valide, cela provoque juste une récursion infinie. –

4

Le problème mentionné ci-dessus entre parenthèses est la source de la récursion infinie. Mais il y a un autre problème avec le code même si vous fixez les parenthèses pour le cas 5 pour être comme le cas 4:

printSeries (4) appelle récursivement printSeries 3 fois. PrintSeries (5) appelle récursivement printSeries 6 fois. PrintSeries (6) appelle récursivement printSeries 12 fois. PrintSeries (10) appelle de manière récursive printSeries 156 fois.
PrintSeries (20) appelle récursivement printSeries 69747 fois. PrintSeries (50) appelle récursivement printSeries plus de 6 trillions de fois. En d'autres termes, votre code fait manière plus de travail que ce qu'il devrait. Voyez-vous pourquoi?

+1

Ouais, il a besoin de lire sur * memoization *. –