Я пытаюсь перевести пример о монадических парсерах (https://www.cs.nott.ac.uk/~gmh/pearl.pdf) в F #.Комбинаторы парсеров F #
До сих пор у меня есть:
type Parser<'a> = Parser of (string -> ('a*string) list)
let item : Parser<char> =
Parser (fun (s:string) ->
match s with
| "" -> []
| null -> []
| _ -> (s.Chars(0),s.Substring 1)::[])
let sat (pred : (char -> bool)) : Parser<char> =
parserWf
{
let! c = item
if pred c then return c
}
let char c : Parser<char> =
sat (fun c' -> c'.Equals(c))
let rec string (str:string) : Parser<string> =
parserWf
{
if (str.Length > 0)
then
let! c = char (str.Chars 0)
let! cs = string (str.Substring 1)
printfn "String: %s" cs
return c.ToString() + cs
else
return ""
}
Если удалить else return ""
из метода string
, то результат всегда пустой список. В Haskell функции строка объявляется:
string :: String -> Parser String
string "" = return ""
string (c:cs) = do {char c; string cs; return (c:cs)}
и это прекрасно работает. Почему функция F # работает не так, как ожидалось?
Вы должны расширить "не работает". Ошибка типа? Ошибка выполнения? Неверный результат? – chi
«Почему функция F # работает не так, как ожидалось [когда я удаляю' else return "" ']?" Ну ... это многое зависит от того, что вы ожидаете. Возможно, вы должны сказать, что это такое. –
Если я удаляю последние буксирные линии строковой функции (иначе возвращаем ""). Тогда, если я делаю «runParser (строка« привет »)« привет! », В F # я получил пустой список, но в Haskell я получил [(« привет »,«! »)]. – user3535953