Parsing 程序错误:未定义的成员:>>;=哈斯克尔

Parsing 程序错误:未定义的成员:>>;=哈斯克尔,parsing,haskell,monads,sequencing,Parsing,Haskell,Monads,Sequencing,我正在Haskell中实现一个简单的解释器,但我有这个问题。代码如下: import Control.Applicative import Data.Char newtype Parser a = P (String -> [(a,String)]) parse :: Parser a -> String -> [(a,String)] parse (P p) inp = p inp item :: Parser Char item = P (\inp -> cas

我正在Haskell中实现一个简单的解释器,但我有这个问题。代码如下:

import Control.Applicative
import Data.Char

newtype Parser a = P (String -> [(a,String)])

parse :: Parser a -> String -> [(a,String)]
parse (P p) inp = p inp

item :: Parser Char
item = P (\inp -> case inp of
    [] -> []
    (x:xs) -> [(x,xs)])

instance Functor Parser where
fmap :: (a -> b) -> Parser a -> Parser b
fmap g p = P (\inp -> case parse p inp of
    [] -> []
    [(v,out)] -> [(g v, out)])

instance Monad Parser where
(>>=) :: Parser a -> (a -> Parser b) -> Parser b
p >>= f = P (\inp -> case parse p inp of
    [] -> []
    [(v,out)] -> parse (f v) out)

three :: Parser (Char,Char)
three = do {x <- item;
    item;
    z <- item;
    return (x,z);}
我得到一个错误:

Program error: undefined member: >>=
有人能帮我吗

  • 不要给实例类型签名

  • 缩进实例定义

  • 在这两件事之后,您将看到一个新的错误,您需要定义一个应用程序实例,因为
    类Applicative m=>Monad m

    编辑:

    你写道:

    instance Monad Parser where
    (>>=) :: Parser a -> (a -> Parser b) -> Parser b    -- This is a type signature
    p >>= f = P (\inp -> case parse p inp of   -- This is the definition
        [] -> []
        [(v,out)] -> parse (f v) out)
    
    第一个问题是类型签名,我通过上面的评论注意到了这一点。删除它:

    instance Monad Parser where
    p >>= f = P (\inp -> case parse p inp of   -- This is the definition
        [] -> []
        [(v,out)] -> parse (f v) out)
    
    第二个问题是压痕。必须缩进成员函数定义(或使用大括号,但这是一种不常见的样式):

    现在,您得到一个新的错误,表示您需要一个应用程序实例。因此,您需要:

    instance Applicative Parser where
        pure = ...
        (<*>) = ...
    
    实例应用程序解析器,其中
    纯=。。。
    () = ...
    

    即使在这之后,它也会告诉您为Functor编写一个实例。

    在声明实例时,您不会显式地编写类型。但是,如果确实要这样做,请打开
    InstanceSigs
    extension:
    {-#LANGUAGE InstanceSigs}

    正如在另一个答案中提到的,Haskell是缩进敏感的,但是您可以将定义放在括号中以绕过它:

    instance SomeClass Int where {
    x = 3
    }
    

    我对这门语言很陌生。我试图理解《haskell编程》一书中描述的内容。你能给我举个例子吗?@paolopast当然可以,请看我的编辑。如果您正在阅读的这本书没有告诉您编写应用程序实例和函子实例,那么它可能已经很旧了。我得到了“表达式中的语法错误(意外的“}”,可能是因为布局不好)”。但我刚刚解决的问题并不存在。这是一个压痕问题。但现在它告诉我如何实现返回函数。我去查一下这本书。非常感谢你@Paolopast是的,
    return
    是将值“放入”monad的函数。在本例中,可能
    返回x=P$\str->[(x,str)]
    。但是,您还需要具有相同定义的
    pure
    。(
    pure
    =
    return
    )。
    instance Applicative Parser where
        pure = ...
        (<*>) = ...
    
    instance SomeClass Int where {
    x = 3
    }