Dato il seguente:Estrazione di una Forse valore nel IO
> (liftM2 fromMaybe) (ioError $ userError "OOPS") (return $ Just "ok")
ghci mi dà
*** Exception: user error (OOPS)
Naturalmente, fromMaybe funziona correttamente:
> (liftM2 fromMaybe) (return $ "not me") (return $ Just "ok")
"ok"
Ma sembra che il L'operazione IO viene eseguita e quindi scartata:
> (liftM2 fromMaybe) (putStrLn "computing.." >> "discarded") (return $ Just "ok")
computing..
"ok"
Perché sta succedendo? C'è un modo per rendere l'IO più pigro?
In particolare, dato value :: IO (Maybe a)
che cosa è un (condensato pulito,) modo di dire
result <- (liftM2 fromMaybe) err value
e lo hanno scompattare provocare o lanciare un IOError di conseguenza?
Grazie per la preoccupazione, ma è un po 'infondata. Sto gettando gli errori in una serie di funzioni di secondo livello che ognuno fa il suo piccolo bit di I/O per prendere qualche configurazione. La funzione di configurazione di primo livello li prova tutti con un "catch" e formatta bene ogni errore. Mi consente di mantenere la gestione degli errori in un'unica posizione senza dover eseguire il threading di una funzione "handleErr" attraverso tutte le funzioni di secondo livello. In uno scenario del genere, gli errori sono ancora una cattiva idea? – So8res
So8res: personalmente avrei le funzioni di secondo livello che producono i valori di 'Maybe', e quindi la funzione di configurazione di primo livello può raggrupparli insieme con qualcosa come' sequence' o '<$>' e '', o gestire ciascuno errore potenziale separatamente, come desiderato. È una questione di gusti, ma a mio parere, gli errori sono quasi sempre una cattiva idea in Haskell, poiché abbiamo potenti astrazioni che ci permettono di comporre 'Maybe'. Il meccanismo di controllo del flusso di tiro/presa non corrisponde allo stile FP che Haskell incoraggia. –