-
Notifications
You must be signed in to change notification settings - Fork 20
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Allow empty CE body and return Zero #1232
Comments
I think this is very reasonable. However, implementation may be a tad trickier than it seems at first, as empty curlies are sometimes valid, for instance: type C =
new() = { } Though I can’t think of anything offhand that would be truly conflicting in cases where there’s a leading ident. PS, under the (absent) section “the current way of doing this”, you could mention that it is legal to have a unit expression. I.e., this is fine: |
This needs a language design suggestion - but please consider it pre-approved. It is a missing case that has come up before but which would be really good to complete. |
@dsyme this is a language suggestion / in the right repo already 🙂 |
Do you mean a RFC in the fslang-design repo @dsyme? |
Yes, any |
That's the next step. I mistakenly thought I was replying to dotnet/fsharp issue |
I propose we allow having empty computation expression bodies that are evaluated with
builder.Zero()
. When no Zero method is available on the builder, a specific error is raised (more specific than the current FS0003).The existing ways of approaching this problem in F# are:
a) Provide a zero/empty function on a module (like
Seq.empty
).b) As @abelbraaksma pointed out below, a unit expression as the only element in the CE body can be used, e.g.
seq { () }
. This works if the builder implements Zero:Pros and Cons
A real-world use case where this makes sense is this: Imagine a HTML DSL that uses CEs and specific builder instances for each HTML element type. It might look like that:
I currently cannot see why (from a syntax point of view) that should not be possible (although I don't know if there are some implementation details that lead to not providing that syntax). It feels natural writing empty bodys of a "thing" when that "thing" has a clear definition of an empty instance (i.e. Zero).
Extra information
Hint: Current errors / messages
Seq (propably due to special compiler treatment for seq) gives a more explicit error on empty CE bodies:
Due to that, I ask myself if this is not something which has obviously "already been decided", but I didn't find anything.
Other builders (e.g. async or hand-rolled builders) give an error that is not very helpful, especially for beginners:
Hint: Generalization
An empty/zero non-function value in a module can have an advantage over the proposed syntax (or the existing
builder {()]
syntax, because non-function values can be generalized, whereas the builder syntax cannot:Hint: Run/Delay awareness
The way of how
builder {}
is transformed into basic language constructs should be similar tobuilder { () }
, which is a not alwassbuilder.Zero()
. The (propably very shortened) ruleset for transformingbuilder { () }
seems to be:Estimated cost (XS, S, M, L, XL, XXL): I can't estimate it based on my knowledge.
Related suggestions: -
Affidavit (please submit!)
Please tick this by placing a cross in the box:
Please tick all that apply:
For Readers
If you would like to see this issue implemented, please click the 👍 emoji on this issue. These counts are used to generally order the suggestions by engagement.
The text was updated successfully, but these errors were encountered: