Visitar URL original
Revisit Computation Expressions design · Issue #140 · fsprojects/FSharpPlus · GitHub
Skip to content

Revisit Computation Expressions design #140

Open

Description

@gusty

I'm opening this issue as a centralized place to discuss and review the current design of the generic Computation Expressions.

The main issue of the current design was highlighted by @cmeeren recently and has to do with the "autosense" design decision, to allow to figure out automatically in many trivial cases the evaluation strategy of the Computation (lazy vs strict).

We can discuss to change it, make it more explicit, or add another set of builders that are more strict and keep backwards compatibility.

Please raise all your questions, opinions, proposals, here.

Activity

  1. wallymathieu commented on Nov 1, 2018

    @wallymathieu
    Member

    I think it would make sense to add some more documentation about MonadPlus. Perhaps something like:

    Monad plus is an additive monad. Use it when you expect one or more results. The name comes from Haskell. See computation-zoo for more information.

  2. wallymathieu commented on Nov 2, 2018

    @wallymathieu
    Member

    I've added a pull request where I've tried to fill in some of the information: #141

  3. added this to the F#+ 2.0 milestone on Jul 21, 2019
  4. wallymathieu commented on Aug 30, 2020

    @wallymathieu
    Member

    Any thoughts on this @cmeeren?

  5. cmeeren commented on Aug 30, 2020

    @cmeeren
    Contributor

    About what? the last update I can see in this issue is from almost 2 years ago.

  6. nikolamilekic commented on Aug 30, 2020

    @nikolamilekic

    I just wanted to add my two cents to this before closing #346.

    I think that computation expressions should not deviate from universally understood concepts as that would surprise and confuse users (especially newbies such as myself). A try...with operation for instance should always handle exceptions and not propagate them (in other words it should behave similarly to the try...with expression outside of a computation expression). This is currently not the case for lazy monads but is the case for strict monads, and I'm hoping this discrepancy will be fixed by any future redesign.

  7. cmeeren commented on Aug 30, 2020

    @cmeeren
    Contributor

    This is currently not the case for lazy monads

    Wait, what? Are you saying that if I replaced the built-in async with monad from FSharpPlus, the exception handling would be very different? That is indeed confusing (and yet another reason I'm sceptical of using the generic CEs from FSharpPlus).

  8. wallymathieu commented on Aug 30, 2020

    @wallymathieu
    Member

    Perhaps in order for a redesign to happen, we need to have some idea about how what kind of design should be suitable. Since v2 is coming up we have more room for breaking changes.

  9. wallymathieu commented on Aug 30, 2020

    @wallymathieu
    Member

    From what I hear it sounds like there would be value in having more strict builders in order to avoid confusion.

  10. gusty commented on Aug 30, 2020

    @gusty
    MemberAuthor

    I think the issue is that try .. with has different requirements when the monad is lazy.

    For a strict monad, we can use the generic try .. with which is already included and working in the monad.strict (or simply monad') generic computation expression.

    Lazy monads on the other hand can't use a generic try .. with and each type needs to provide a specific TryWith implementation.

    At the moment we have to educate the user to prevent him to write such code but ideally a workflow that is not lazy over a type that doesn't provide a TryWith method should not compile and throw a compiler error stating that.

    I'm not sure if that's achievable, maybe if we move the generic TryWith from the Monad file to the strict builders and replace them with a compiler error message will address the issue, at the cost of removing the possibility of customizing the TryWith for strict monads.

    @nikolamilekic even withouth this library, try .. with is used in all common F# lazy monads, namely the built-in seq and async.

  11. gusty commented on Aug 30, 2020

    @gusty
    MemberAuthor

    Actually, looking at the code, we already call a generic try with for strict builders.
    So, all we have to do is to fail at compile-time in the generic TryWith

    See #347

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions