foo:: Int -> Int -> Int
foo z x = if (z < 100)
then z * foo (z+(x*z)) z
else z
How would you print out(the integer z) an output every time it gets called from itself?Can you have function that returns an IO and Int? Do you need a secondary function?
4 Réponses :
Toute fonction qui effectue des E / S doit renvoyer son résultat dans le remarque que les deux branches du Ce n'est pas la même chose que le retour "An io code> monad: si code > expression doit maintenant être dans io code> aussi. p> io code> et int code> int code> ". io int code> est le type d'une valeur qui représente une action d'E / S qui, lorsqu'elle est exécutée, produira un int code> comme résultat (éventuellement après avoir effectué des E / S) . Donc la définition ci-dessus de foo code> prend un int code> et un int code> et renvoie une action d'E / S qui finira éventuellement à un int code>. p> p>
Pour la simplicité, vous pouvez utiliser Trace . Cependant, il n'est pas accueilli pour un code de production réel car il brise la transparence référentielle.
trace code> prend une chaîne code> pour imprimer et une valeur à renvoyer. import Debug.Trace
foo:: Int -> Int -> Int
foo z x = trace ("z = " ++ show z) $ if (z < 100)
then z * foo (z+(x*z)) z
else z
*Main> foo 1 2
z = 1
z = 3
z = 6
z = 24
z = 168
72576
Pour la complétude, je vais répondre à cette question:
Pouvez-vous avoir une fonction qui renvoie un IO et INT? P> BlockQuote>
... Littéralement. La réponse est "oui!" ... et c'est même parfois utile. Probablement ce n'est pas ce que vous voulez faire en tant que débutant, mais au cas où il est, voici un échantillon. P>
xxx pré> Par exemple, vous pouvez imprimer les appels récursifs en réglant p>
xxx pré> ou vous pouvez simplement imprimer la réponse en réglant P>
xxx pré> ou une demi-douzaine d'autres choses. Bien sûr, le type
io () code> est un peu difficile à inspecter; Vous pouvez envisager d'écrire quelque chose comme ça à la place: p>xxx pré> Utilisation est assez similaire à celui ci-dessus, mais avec un
ExtraRunwriter code> dans; Par exemple, vous pouvez écrire l'un de ces deux: p>xxx pré> L'avantage de cette méthode est que vous récupérez une liste des valeurs d'appel plutôt que d'une action IO qui imprime que liste, afin que vous puissiez munier les appels de nombreuses manières plus intéressantes. p> p>
+1 Nos débutants Haskell devraient être introduits à des choses comme écrivain code> beaucoup plus tôt que nous les enseignons habituellement.
@Danburton, si nous introduisons x plus tôt, nous devons présenter y plus tard. Quel est Y dans ce cas?
Les compréhensions de liste IMHO @Luqui sont apprises trop tôt. Il est vrai qu'ils sont assez simples de comprendre, mais il est préférable que l'étudiant puisse apprendre l'interface monad réelle puis découvrez la compréhension de la syntaxe de la syntaxe de la compréhension. J'espère que la rédaction de vos propres typeclasses et de vos propres cas devriez venir plus tard, bien que je n'ai pas beaucoup réfléchi aux ramifications de cela.
@Luqui: Je suppose que debug.trace.trace.trace alors
Pourriez-vous commenter les implications de la performance de l'utilisation de écrivain code> avec une liste au lieu d'un dlist code>?
bâtiment de la réponse de @ is7s, une idiome utile pour utiliser ici, nous avons introduit une définition de débog.trace code> est de faire ceci: FOO CODE> avec le TRACE CODE> dans un protège qui évalue vers FALSE code>, de sorte qu'il va toujours tomber à la définition initiale. De cette manière, nous ne perturons pas notre fonction et pouvons transformer le traçage sur ou éteindre en commentant la ligne. P> p>