Why does F# not have built-in apply, map, and bind functions for types such as 'Result' and 'Async'?
Not much of a reason other than a concrete proposal for the full set of Result functions simply wasn't added: https://github.com/fsharp/fslang-design/issues/49#issuecomment-206822451
There's already a bind and map function for Result, so in this case it's just a matter of apply being added for you. But as you'll quickly find if you make a proposal, there's a broader set of functionality to consider.
Related
I am using System.Linq.Dynamic.Core to parse custom statistical templates, and was wondering if it is possible to somehow extend the library's functionality to parse more mathematical functions. Specifically, I needed in this instance to calculate the absolute value of a variable. I have managed to do this with the already supported "iif" function (i.e. "iif(a>-a, a, -a)"), but I was wondering if there is a way to extend the library to add an "abs()" function, and similarly other functions I may need in the future (such as square root etc).
Any pointers to the right direction?
The System.Linq.Dynamic.Core library is not really designed for this extensibility.
However, you can take a look at the System.Linq.Dynamic.Core.Parser.ExpressionParser.cs for examples, like the IIF you already mention.
Suppose one needs a numeric data type whose allowed values fall within a specified range. More concretely, suppose one wants to define an integral type whose min value is 0 and maximum value is 5000. This type of scenario arises in many situations, such as when modeling a database data type, an XSD data type and so on.
What is the best way to model such a type in F#? In C#, one way to do this would be to define a struct that implemented the range checking overloaded operators, formatting and so on. A analogous approach in F# is described here: http://tomasp.net/blog/fsharp-custom-numeric.aspx/
I don't really need though a fully-fledged custom type; all I really want is an existing type with a constrained domain. For example, I would like to be able to write something like
type MyInt = Value of uint16 where Value <= 5000 (pseudocode)
Is there a shorthand way to do such a thing in F# or is the best approach to implement a custom numeric type as described in the aforementioned blog post?
You're referring to what are called refinement types in type theory, and as pointed out by Daniel, look for F*. But it is a research project.
As far as doing it with F#, in addition to Tomas' post, take a look at the designing with types series.
My suggestion would be to implement a custom struct wrapping your data type (e.g., int), just as you would in C#.
The idea behind creating this custom struct is that it allows you to "intercept" all uses of the underlying data value at run-time and check them for correctness. The alternative is to check all of these uses at compile-time, which is possible with something like F* (as others mentioned), although it's much more difficult and not something you would use for everyday code.
Which way is more idiomatic to use Nullable<'a> or to use Option<'a> for representing a nullable int?
Option is far more idiomatic in F# code.
It has far nicer syntax when used in match and has large amounts of support from the standard library.
However, if you plan to access the code from C# or some other language you should probably expose the interface with Nullable which is easier to use in C#.
As John said, Option<T> is definitely more idiomatic type in F#. I would certainly use options as my default choice - the Option module provides many useful functions, pattern matching works nicely on options and F# libraries are generally designed to work with options.
That said, there are two cases when you might want to use nullable:
When creating arrays of optional values - Nullable<T> is a value type (sort of) and if you create an array Nullable<T>[] then it is allocated as continuous memory block. On the other hand options are reference types and option<T>[] will be an array of references to heap-allocated objects.
When you need to write some calculations and propagate missing values - in F# 3.0, there is a module Microsoft.FSharp.Linq.NullableOperators which implements various operators for dealing with nullable values (see MSDN documentation) which lets you write e.g.:
let one = Nullable(1)
let two = Nullable(2)
// Add constant to nullable, then compare value of two nullables
(one ?+ 2) ?>=? two
I have implemented IEnumerable for a collection I built, and (although I have not tested them all) the Seq values appear to work correctly. Is it possible to override some Seq values, for instance "last", when the native performance of a value of my collection is better than using Seq's IEnumerable based function? I have not found any information on overriding Seq.
No -- the functions in the Seq module can't be overridden. However, some of them do try to optimize performance by checking their input value (the seq<'T> instance you pass them) to see if it's an instance of IList<'T> or 'T[]; if it is, the functions will take some optimized code path. For example, if you pass an array ('T[]) to Seq.length, it'll be able to quickly determine the length by using the .Length property of arrays.
If you're stuck on using the Seq module, the only performance optimization I can think of would be to have your collection also implement ICollection<'T> and/or IList<'T>. That may optimize some cases, but it won't be all cases.
As already said in the other answer, there is no way you can override the functions in the Seq module. If you're implementing a custom collection, then the best thing to do is to follow the standard pattern used by the core F# libraries.
The Seq module contains the most often used functions and functions that can be reasonably provided for any sequence.
Modules like Array or List provide more efficient implementations for a specific collection type and they add more functions (not available in Seq) that are specific to the collection (for example, functions List.tail and Array.get).
The best way when adding your own collection is to follow this pattern:
Implement IEnumerable<'T> so that the functions from Seq module work for your type
Create MyCollection module that contains efficient implementations of standard functions (at least those that matter to you) and adds more functionality that is specific to your collection.
This is a question just out of curiosity: when you implement a workflow factory, you don't do it as an interface implementation, but rather just make sure the function signatures of the monad functions match. Is there a design reason for this?
For one thing, the lack of higher-kinded types in .NET means that you can't give the methods useful signatures. For instance, ListBuilder.Return should have type 't -> 't list, while OptionBuilder.Return should have type 't -> 't option. There's no way to create an interface with a Return method that has a signature supporting both of these methods.
I think that the lack of higher-kinded types as mentioned by kvb is probably the main reason. There are ways to workaround that, but that makes the code a bit obscure (see this snippet).
Another reason is that F# computation expressions allow you to define different combinations of methods. It's not always just Bind and Return. For example:
Some define Yield, YieldFrom, Combine to allow generating results
Some define Return, ReturnFrom, Bind to define a monad
Some define Return, ReturnFrom, Bind, Combine to define a monad that can return multiple things
Some also define Delay or Delay and Run to handle laziness
... so computation expressions would need to be defined as quite a few different interfaces. I think the current design leaves some nice flexibility in what features of computations you can support.