2010-12-13 41 views
2

Bonne journée! Notre professeur nous a demandé de déterminer si un mot ou une série de nombres est un palindrome ou n'utilise pas de piles. J'ai déjà fini de faire ça. Mais je veux m'entraîner davantage maintenant j'essaie de déterminer si une phrase est un palindrome ou non en enlevant des espaces et d'autres caractères non pertinents (Note: Ne fait plus partie de mes devoirs) Mon code fonctionne déjà (j'espère) mais je trouve c'est désordonné. Donc je veux l'améliorer. Je veux supprimer la fonction goto car mon professeur m'a conseillé de ne pas l'utiliser. Comment puis-je sortir de l'instruction if sans utiliser la fonction goto? Merci d'avance. Aussi existe-t-il d'autres façons de vérifier si une phrase est un palindrome ou non parce que mon code est fait dans une méthode brute force. Mon code est le suivant: NOTE (je ne comprend pas/collé le struct et la pop et la fonction push ici)Palindrome - enlever le goto

int main(){ 
    char word[11]; 
    char temp[11]; 
    char value; 
    int i=0, x=0, n=0, length=0; 
    Stack*head = NULL; 
    printf("Please type the word: "); 
    gets(word); 
    length = strlen(word); 
    while(i<length){ 
     if(isspace(word[i]) || !isalpha(word[i])) { 
      if(isdigit(word[i])) goto NEXT; // i used the goto function here 
      i++; 
      continue; 
     } 
     NEXT: 
     temp[n]=word[i]; 
     push(&head, word[i]); 
     i++; 
     n++; 
    } 
    temp[n]='\0'; 
    while(x<n){ 
     value = pop(&head);   
     if (value==temp[x]){ 
      x++; 
      continue; 
     } 
     break; 
    }  
    if(x==n) printf("Yehey! It is a palindrome."); 
    else printf("Sorry, It is not a palindrome."); 
    getch(); 
} 

Sur la base de vos suggestions. Voici mon code amélioré:

int main(){ 
    char word[11]; 
    char temp[11]; 
    int i=0, n=0; 
    int flag = 1; 
    Stack*head = NULL; 
    printf("Please type the word: "); 
    fgets(word, 11, stdin); 
    for(i = 0; word[i]!='\0' ; i++){ 
     if(isalnum(word[i])) { 
      temp[n]=word[i]; 
      push(&head, word[i]); 
      n++; 
     } 
    } 
    temp[n]='\0'; 
    for(i=0; temp[i]!='\0'; i++){ 
     if (pop(&head)!=temp[i]){ 
      flag = 0; 
      break; 
     } 
    }  
    if (flag==1) printf("Yehey! It is a palindrome."); 
    else printf("Sorry, It is not a palindrome."); 
    getch(); 
} 
+3

Je voudrais également vous conseiller de cesser d'utiliser la fonction gets(). Utilisez fgets() à la place, afin de ne pas casser votre pile si vous entrez 11 caractères ou plus. – BatchyX

Répondre

2

J'aime votre attitude. Premièrement, ce que vous essayez de faire ici est d'imbriquer deux instructions logiques qui sont essentiellement une. Vous utilisez également les mauvaises fonctions pour déterminer le type de caractère:

si isspace(word[i]) alors vous pouvez garantir que !isalpha(word[i]). Les deux déclarations seront toujours vraies ou fausses en même temps, donc l'une d'entre elles est redondante. Qu'est-ce que vous faites vraiment ne pousse que des caractères si le sont alphanumériques, non? Donc, plutôt que d'avoir une instruction if pour déterminer si vous voulez ignorer un caractère, vous devriez faire une instruction if pour déterminer si vous voulez pousser le caractère. Je pense que isalnum() pourrait être ce que vous voulez.

En second lieu, plutôt que de faire strlen() qui effectue une itération sur la chaîne et en utilisant la valeur de retour à itérer sur la chaîne (qui fait deux fois) essayer:

while('\0' != word[i]) 

ou mieux encore:

for(i = 0; '\0' != word[i]; i++) 

Enfin, votre test pour un palindrome pourrait être revu à la hausse. Tester une valeur de boucle après la boucle fonctionne dans tous les cas mais est un peu moche. Il ne tolère pas volontiers les imbéciles. Dans un environnement professionnel, beaucoup de personnes, dont certaines ne sont pas si consciencieuses, éditent le code, et l'utilisation de valeurs de boucle après une boucle peut être risquée. Peut-être plutôt avoir un bool appelé quelque chose comme "match" et l'initialiser à true, puis boucle jusqu'à la fin de la pile ou "match" tourne false et mettre "match" à false si le caractère de la pile ne "correspond" pas au valeur attendue. Ce sera également plus efficace. J'étais en train de composer cette réponse quand la question originale a apparemment été supprimée.

Si vous voulez que je poste un exemple de code, je suis heureux de le faire, mais je pense que vous pourriez en apprendre plus si je ne le fais pas. Si vous voulez un exemple de code, ou si vous voulez voir ce que vous venez de trouver après cette réponse, n'hésitez pas.

+0

désolé de la suppression de ma question précédente .. :) – newbie

+0

@Newbie: Pas de soucis. J'ai fini de le mettre à jour maintenant. – AlastairG

+0

J'ai déjà posté mon code amélioré .. merci – newbie

4

Le changement plus simple que vous pouvez faire est la suivante:

... 
    if(isspace(word[i]) || !isalpha(word[i])) { 
     if(!isdigit(word[i])) { 
      i++; 
      continue; 
     } 
    } 
    temp[n]=word[i]; 
    ... 

Il y a quelques autres choses que vous pouvez faire pour ranger le code (par exemple, croisez les if, se débarrasser des isspace depuis !isalpha couvre cela et ainsi de suite).

+0

@aix je ne peux pas utiliser le continue .. huhuhhu parce qu'il va sauter le temp [n] = mot [i]; pousser (& la tête, mot [i]); i ++; n ++; ?? – newbie

+0

Pourquoi ne pas simplement concaténer les deux instructions 'if'? – AlastairG

+0

@aix je veux inclure les chiffres aussi .. – newbie

0

Pour un tel saut court, il est trivial de réécrire pour supprimer le problème.

while(i<length){ 
    if(isspace(word[i]) || !isalpha(word[i])) { 
     if(!isdigit(word[i])) { 
      i++; 
      continue; 
     } 
    } 
    temp[n]=word[i]; 
    push(&head, word[i]); 
    i++; 
    n++; 
} 
+0

Même réponse que trois personnes précédentes et toujours pas de concaténation des instructions 'if'. Ou supprimer le test redondant. 'if (! isalnum (mot [i]))' est équivalent aux instructions 'if' ici, et toujours pas la meilleure solution globale. – AlastairG

+0

@AlastairG: Il a demandé de l'aide pour un problème spécifique, et je l'ai résolu. S'il veut le reste, il peut demander. – Puppy

+0

@DeadMD: Elle a dit qu'elle voulait améliorer tout son code et supprimer spécifiquement le "goto". Elle a également précisé qu'elle était étudiante et même si elle avait seulement posé des questions sur le "goto", alors que techniquement votre réponse serait correcte, elle ne serait pas "utile" car elle n'enseigne pas la meilleure solution. – AlastairG

1

Je viens jeta un regard over..might être mal compris:

while(i<length){ 
    if(isalnum(word[i])) { 
     temp[n]=word[i]; 
     push(&head, word[i]); 
     n++; 

    } 
    i++; 

}

+2

Mieux, mais il n'y a pas besoin de continuer, et le «i ++» est commun aux deux parties, donc sortez-le de l'instruction «if ... else». Aussi 'isalnum()' est identique à 'isalpha() || isdigit() '. – AlastairG