Как отобразить результаты ОК

Я играю с примерами вяза, и я заметил, что пример поля дает Result типы. Застряв, я придумал этот упрощенный случай:

import Html exposing (text)
import String

f: Int -> Int
f x = x + 1

g: Result String Int -> Result String Int
g x = (Result.map f) x

main =
  text (  toString ( g  (String.toInt 5 ) ))

Результат отображается OK 6 и я бы предпочел, чтобы это отображалось просто 6 -- Я знаю это toString принимает любой тип и возвращает строковое представление о нем. Так что, возможно, я могу изменить toString

  • если результат OK тогда я могу напечатать числовой результат
  • если результат Err тогда я хотел бы сделать несколько пользовательских сообщений об ошибках

Возможно, это причина andThen так как + 1 операция может потерпеть неудачу.

andThen : Result e a -> (a -> Result e b) -> Result e b
andThen result callback =
    case result of
      Ok value -> callback value
      Err msg -> Err msg

Определение andThen это именно то, что он делает... и является примером case,

Либо с andThen или старый case как мне исправить мой пример? Даже если я исправлю это сам, это может быть не самое подобное Elm решение с хорошей обработкой ошибок. Итак, я отправляю вопрос.

1 ответ

Когда функция возвращает Result, у вас есть выбор - вы также можете вернуть Result, и в этом случае вы можете вернуть Err(что-то) или Ok(что-то). Это просачивает ваши ошибки вплоть до вызывающей функции, которая может решить, что делать. Другой способ - вы можете вернуть что-то, что не является результатом, например, String или Html. Если вы идете по этому второму маршруту, то вам нужно использовать обе возможности Результата и при этом возвращать строку или HTML.

Так, например, эта функция принимает результат и возвращает строку. Он обрабатывает обе возможности, возвращая строку, даже если результатом был Err.

foo: Result String Err -> String
foo myres = 
  case myres of 
    Ok(str) -> str
    Err(e) -> "there was an error! uh oh"

Это своего рода вопрос о том, как далеко вверх по иерархии вы хотите пойти с вашим результатом. Вы хотите, чтобы ошибки проникали до самого верхнего уровня? Может быть, ваша функция верхнего уровня выглядит так:

View: Model -> Html
View model = 
  case makeMyHtml(model) of 
    Ok(htm) -> htm
    Err(e) -> renderSpecialErrorHtmlPage(e)

В любом случае, чтобы избавиться от "Ok", в этом случае вы можете сделать это:

main =
  let res = g  (String.toInt 5 ) 
  text (  toString ( Result.withDefault "g returned an error!" res)) 

Если g возвращает Ok(6), вы получаете "6", но если он возвращает ошибку, вы получаете "g вернул ошибку!".

Другие вопросы по тегам