Question

j'apprends maintenant SICP et faire la ex2.23 J'ai wrirten le code suivant:

(define (for-each proc items)
   (if (null? items)
       #t
       ((proc (car items))
        (for-each proc (cdr items)))))

mais lors de l'exécution, l'erreur de la cause: application procédure: la procédure prévue, donnée: #; arguments étaient les suivants: ()

Je crois que je connais la raison: je l'appelle pour-chaque fonction récursive, tous appelés for-each voulait retourner la valeur

mais quand je l'ai modifié le code:

(define (for-each proc items)
  (cond ((null? items) #t)
        (else (proc (car items)) (for-each proc (cdr items)))))

il fonctionne bien. Je ne comprends pas, pourquoi? cond , fait tous appelé à-chaque pas besoin de retourner la valeur?

i utilisé DrScheme et choisir la langue SICP

Je ne suis pas un locuteur natif de l'anglais, donc s'il y a qqch qui n'est pas décrit clairement, merci de me dire

Était-ce utile?

La solution

  

mais lors de l'exécution, erreur Cause: application procédure: attendue> procédure, donnée: #; arguments étaient les suivants: ()

     

Je crois que je connais la raison: je l'appelle pour-chaque fonction récursive,> tous appelé for-each voulait retourner la valeur

Non, c'est parce que dans la clause alternative de if vous avez la ((proc (car items)) (for-each proc (cdr items))) combinaison. Vous l'intention d'évaluer les deux combinaisons (proc (car items)) et (for-each proc (cdr items)) séquentiellement, et à cette fin que vous avez pensé de les mettre dans une autre paire de parenthèses travailleraient. Mais en réalité, ce que vous avez spécifié est que le résultat de (proc (car items)) est une procédure à appliquer à l'argument qui est la valeur de retour de (for-each proc (cdr items)). Ce n'est pas le cas, et vous obtenez une erreur. La clé étant de point entre parenthèses dans Lisp ne sont pas pour le regroupement, mais ont une signification précise.

Le problème est que if ne peut avoir qu'une seule combinaison dans cette position, alors que vous voulez avoir deux fois de suite. D'autre part, cond ne souffre pas d'une telle restriction; vous pouvez mettre aussi longtemps une séquence de combinaisons individuelles dans la partie conséquente d'une clause de cond que votre coeur désire. Cet état de choses est tout simplement la façon dont la langue est définie au travail.

Vous pouvez tout aussi bien utiliser cond dans ces situations, mais si vous voulez continuer à utiliser if il y a quelques options pour bourrer multiples combinaisons en un seul. Par exemple. vous pouvez créer une procédure lambda dont le corps est les deux combinaisons et le feu immédiatement hors tension:

(define (for-each proc items)
   (if (null? items)
       #t
       ((lambda ()
          (proc (car items))
          (for-each proc (cdr items)) )) ))

Vous pouvez aussi utiliser begin qui est en fait destiné à être utilisé à cette fin:

(define (for-each proc items)
   (if (null? items)
       #t
       (begin
          (proc (car items))
          (for-each proc (cdr items)) ) ))
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top