F# 5 update for August
We’re excited to announce more updates to F# 5 which will go alongside .NET 5 preview 8! We’ve shipped various updates since the beginning of this year:
Today, we’re pleased to announce the completion of the F# 5 feature work. There is one minor enhancement planned for the .NET 5 RC, but other than that we are finished with F# 5! From this point forward, our journey to shipping F# 5 will be focused mostly on bug fixes and addressing feedback.
You can get the latest F# 5 in these ways
- Install the latest .NET 5 preview SDK
- Install .NET for Jupyter/nteract
- Install .NET for VSCode Notebooks
If you’re using Visual Studio on Windows, you’ll need both the .NET 5 preview SDK and Visual Studio Preview installed.
Using F# 5 preview
If you’re using the .NET 5 preview SDK, check out the sample repository which shows off some of what you can do with F# 5. You can play with each of the features there instead of starting from scratch.
If you’d rather use F# 5 in your own project, you’ll need to add a
LangVersion property with
preview as the value. It should look something like this:
Alternatively, if you’re using Jupyter Notebooks and want a more interactive experience, check out a sample notebook that shows the same features, but has a more interactive output.
This preview adds String Interpolation, one of the most highly-requested language features and the very first feature that we had an initial design for in the F# Language Design repository. The design has undergone a lot of discussion over the years, but finally a breakthrough on how to best handle it was made by Yatao Li, who also supplied an initial implementation.
However, F# interpolated strings also allow for typed interpolations, just like the
sprintf function, to enforce that an expression inside of an interpolated context conforms to a particular type. It uses the same format specifiers.
Support for nameof is now complete
In the June update, we mentioned that we were finishing up several design changes for
nameof. These are now complete!
nameof resolves the symbol it’s being used for and produces a name that represents what it’s called in F# source. This is useful in various scenarios, such as logging, and protects your logging against changes in source code.
The last line will throw an exception and "month" will be shown in the error message.
You can take a name of nearly everything in F#:
Three final additions are changes to how operators work: the addition of the
nameof<'type-parameter> form for generic type parameters, and the ability to use
nameof as a pattern in a pattern match expression.
nameof<'type-parameter> form aligns with how
typedefof work in F# today.
Open Type declarations
This preview also adds Open Type Declarations. It’s like Open Static Classes in C#, except with some different syntax and some slightly different behavior to fit F# semantics.
With Open Type Declarations, you can
open any type to expose static contents inside of it. Additionally, you can
open F#-defined unions and records to expose their contents. This can be useful if you have a union defined in a module and want to access its cases, but don’t want to open the entire module.
Overloads of custom keywords in computation expressions
Computation expressions are a powerful feature for library and framework authors. They allow you to greatly improve the expressiveness of your components by letting you define well-known members and form a DSL for the domain you’re working in.
We’ve enhanced computation expressions to allow for Applicative forms already. This time, Diego Esmerio and Ryan Riley contributed a design and implementation to allow for overloading custom keywords in computation expressions. This new feature allows code like the following to be written:
Prior to this change, you could write the
InputBuilder type as it is, but you couldn’t use it the way it’s used in the previous example. Since overloads, optional parameters, and now
System.ParamArray types are allowed, everything just works as you’d expect it to.
Thanks, Diego and Ryan!
Interfaces can be implemented at different generic instantiations
The final feature enabled in this preview is an enhancement to interfaces in F#. You can now implement the same interface at different generic instantiations. Lukas Rieger contributed an initial design and implementation of this feature.
Finishing F# 5
Now that we’re feature complete for F# 5, minus a tweak here or there, we’re going to shift our focus:
- Address bug fixes and high-priority feedback items for F# 5
- Improve our engineering system in the F# development repository, particularly to improve our testing infrastructure so that it’s easier for open source contributors to work there
After F# 5 ships alongside .NET 5, we’ll also start our planning for the next wave of F# investments. We’d love for you to join us when we get there.
Cheers, and happy F# coding!