簡體   English   中英

無法將預期類型'a - > Int'與實際類型'IOArrow String Int'匹配

[英]Couldn't match expected type ‘a -> Int’ with actual type ‘IOArrow String Int’

我試圖理解箭頭並創建以下示例:

{-# LANGUAGE Arrows #-}


module Main where

import Control.Arrow
import Control.Monad
import qualified Control.Category as Cat
import Data.List
import Data.Maybe

data IOArrow a b = IOArrow { runIOArrow :: a -> IO b }

instance Cat.Category IOArrow where
  id = IOArrow return
  IOArrow f . IOArrow g = IOArrow $ f <=< g

instance Arrow IOArrow where
  arr f = IOArrow $ return . f
  first (IOArrow f) = IOArrow $ \(a, c) -> do
    x <- f a
    return (x, c)

foo :: Int -> String
foo = show

bar :: String -> IO Int
bar = return . read

main :: IO ()
main = do
  let f = arr (++"!!") . arr foo . IOArrow bar . arr id
  result <- runIOArrow f "123"
  putStrLn result 

編譯器抱怨:

    • Couldn't match expected type ‘a -> Int’
                  with actual type ‘IOArrow String Int’
    • Possible cause: ‘IOArrow’ is applied to too many arguments
      In the first argument of ‘(.)’, namely ‘IOArrow bar’
      In the second argument of ‘(.)’, namely ‘IOArrow bar . arr id’
      In the second argument of ‘(.)’, namely
        ‘arr foo . IOArrow bar . arr id’
    • Relevant bindings include
        f :: a -> [Char] (bound at app/Main.hs:32:7)
   |
32 |   let f = arr (++"!!") . arr foo . IOArrow bar . arr id
   |                                    ^^^^^^^^^^^


    • Couldn't match expected type ‘IOArrow [Char] String’
                  with actual type ‘a0 -> [Char]’
    • Probable cause: ‘f’ is applied to too few arguments
      In the first argument of ‘runIOArrow’, namely ‘f’
      In a stmt of a 'do' block: result <- runIOArrow f "123"
      In the expression:
        do let f = arr (++ "!!") . arr foo . IOArrow bar . arr id
           result <- runIOArrow f "123"
           putStrLn result
   |
33 |   result <- runIOArrow f "123"
   |                        ^  

我究竟做錯了什么?

你想要(.) :: Category cat => cat bc -> cat ab -> cat ac來自Control.Category (.) :: Category cat => cat bc -> cat ab -> cat ac ,但你最終使用(.) :: (b -> c) -> (a -> b) -> (a -> c)來自Prelude

  • 啟用NoImplicitPrelude然后導入Prelude顯式隱藏id(.)
  • 導入Control.Category不合格(或遭受Cat..無處不在)

額外獎勵: arr id只是來自Control.Catgory id

{-# LANGUAGE Arrows, NoImplicitPrelude #-}

module Main where

import Prelude hiding ((.), id)
import Control.Arrow
import Control.Monad
import Control.Category
import Data.List
import Data.Maybe

data IOArrow a b = IOArrow { runIOArrow :: a -> IO b }

instance Category IOArrow where
  id = IOArrow return
  IOArrow f . IOArrow g = IOArrow $ f <=< g

instance Arrow IOArrow where
  arr f = IOArrow $ return . f
  first (IOArrow f) = IOArrow $ \(a, c) -> do
    x <- f a
    return (x, c)

foo :: Int -> String
foo = show

bar :: String -> IO Int
bar = return . read

main :: IO ()
main = do
  let f = arr (++"!!") . arr foo . IOArrow bar . id
  result <- runIOArrow f "123"
  putStrLn result 

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM