dis que je voulais créer une enveloppe pour disons maintenant que je voulais construire une valeur par défaut pour que "maintenant", par exemple p> ceci (évidemment) échoue avec: P> ⢠Couldn't match expected type âUTCTimeâ
with actual type âIO UTCTimeâ
⢠In the first argument of âCustomDateStampâ, namely âgetCurrentTimeâ
In the expression: CustomDateStamp getCurrentTime def
In an equation for âdefâ: def = CustomDateStamp getCurrentTime def
|
98 | def = CustomDateStamp getCurrentTime def
| ^^^^^^^^^^^^^^
3 Réponses :
à une première approximation: vous ne pouvez pas faire ça. Une fois dans IO, toujours en Io (et il y a déjà une instance code> par défaut code> pour io a code> qui ne fait pas ce que vous voulez). Cuisson un plan différent. P>
Techniquement, vous peut I> le faire avec USAfe-io, mais cela ne fonctionnera pas comme vous vous attendez.
Oui, il y a une deuxième approximation qui est différente de celle du premier. Mais ma réponse et ma recommandation sont debout.
Pensez-vous que la par défaut (io a) code> instance fournie "devrait" être là à partir d'un point de vue de conception? Je suppose que cela donne une commodité parfois, au coût de la prévention des cas de défaillance - (IO -) - des instances de l'environnement?
@moongoose Les instances d'IO et de fonctions Synergize bien: des bibliothèques qui prennent un rappel, disent, keyEvent -> io () code>, peuvent être facilement donnés
def code> et c'est une valeur déforme sensée. (essentiellement, ignorer l'événement et ne rien faire). Je pense que je suis assez bien excluant les instances qui font l'Io actuel; En dépit d'aimer code> par défaut code> plus que la plupart des haskellers, et donc probablement l'utilisant plus que la plupart des choses, je n'ai vraiment ressenti vraiment aucune douleur de exclure des exemples d'IO passionnantes.
Etant donné que sauf getCurrenttime :: ut uttique code> Vous ne pouvez pas simplement l'appeler. Il n'y a pas de fonction avec type
io a -> a code> p>
inadaperformio code> (et d'autres trucs magiques comme celui-ci). Je vous décourage fort de prendre cette route. P>
Cela ne fonctionnera toujours pas comme la puissance attend. En fonction des raisons, ce sera parfois le réel actuel, d'autres fois, ce sera un point sur le passé.
En effet, il n'y a pas de moyen significatif comment cela peut fonctionner, mais cela fonctionnera en première approximation. Parce que le compilateur ne cache pas le résultat d'appel de la fonction.
@talex, les résultats des appels de fonction ne sont pas mis en cache, mais cela n'est pas considéré comme un appel de fonction dans ce contexte. Sans optimisation, il sera mis en œuvre à l'aide d'un appel de fonction (appliquer un argument de dictionnaire) et donc vraisemblablement pas mis en cache. Avec l'optimisation, le spécialisateur souleva presque certainement l'appel au niveau supérieur et exécutez l'action io code> uniquement la première fois qu'un horodatage est demandé.
Le conseil habituel s'applique. Commencer les programmeurs Haskell ne devrait pas utiliser aucun danger dangereux io code> (sauf ce qui est dans
débog.trace code>). Les programmeurs de Haskell avancés savent qu'ils ne devraient presque jamais utiliser
io code>. Il y a un très petit nombre i> de situations où les programmeurs avancés savent qu'ils peuvent l'utiliser en toute sécurité (généralement en combinaison avec le FFI). Dans le reste, ils prendront des soins extrêmes et peuvent bien expédier du code subtilement de buggy jusqu'à ce que quelqu'un vous déclenche. Oui, cela inclut les programmeurs de Haskell avancés qui ont écrit le système d'exécution GHC; Ce genre de choses est dur i> pour avoir raison.
Je jetterais dans le mélange que vous pouvez écrire ceci pour un type dans lequel la valeur par défaut nécessite une action IO, (facilement réglable pour par exemple, une pile MTL). Un peu controversé parce que le chevauchement est méchant. P> edit: nécessite se chevauchant code>,
io CustomDateStamp code> est plus spécifique que
io a code> devrait sélectionner cette instance en cas de portée. p> p>
Je conviens que cela serait raisonnable dans un monde hypothétique dans lequel les cas qui se chevauchent sont raisonnables. Nous ne vivons pas dans ce monde, cependant.
Ce n'est pas une bonne idée. Dans un langage paresseux, il est très difficile de prédire lorsque les expressions sont évaluées, mais nous ne nous soucions pas de ce que la pureté garantit que le résultat final est le même. Votre instance casse cette propriété:
let t = def in (t, t) code> ne devient plus équivalent à
(def, def) code>, car ce dernier peut être évalué avec une paire avec une paire avec une paire différents composants. Plus de manière pragmatique,
def code> ne peut être évalué qu'à l'heure imprimée à l'écran au lieu de la création-temps, causant des horodatages très perplexes.