I'm pretty sure this isn't possible but thought I'd double check. I guess I'm trying to mimic typescript's union types.
I have a type
type StringOrInt =
| String of string
| Int of int
And then a function
let returnSelf (x: StringOrInt) = x
At the moment the function has to be called like
returnSelf (String "hello")
Is it possible to do
returnSelf "hello"
and infer that it is a valid StringOrInt?
At the moment it's not supported out of the box, but fairly simple generic casting method can be implemented.
Given an example function:
let call v = (* v has inferred type StringOrInt *)
match v with
| String s -> printfn "called a string %s" s
| Int i -> printfn "called an int %i" i
We could eventually call it like so:
(* % is a unary prefix operator *)
call %"abc"
call %1
We need to provide some way to tell how to convert ordinary string/int into StringOrInt type. This can be used by exemplar convention call:
type StringOrInt =
| String of string
| Int of int
static member inline From(i: int) = Int i
static member inline From(s: string) = String s
Here our discriminated union provides two static methods which are responsible for casting. Since they correspond to the same naming convention, we can use them together with F# statically resolved generic type parameters - these are generics that are resolved at compile time unlike the .NET generics which exists also at runtime - to create a casting function (or operator):
(* casting operator *)
let inline (~%) (x: ^A) : ^B =
(^B : (static member From: ^A -> ^B) x)
This way you can use % prefix operator over any type that implements a casting mechanism in form of static From method.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With