I have this generic function in F# that uses (-) operator:
let inline sub a b = a - b
Now I'm calling this function from C#:
int a = sub<int, int, int>(4, 1);
This raises an error:
Unhandled Exception: System.NotSupportedException: Specified method is not supported. at ProjA.MainClass.Main (System.String[] args) [0x00000] in <4f209fa43741462db3b8f73ac83c35a2>:0 [ERROR] FATAL UNHANDLED EXCEPTION: System.NotSupportedException: Specified method is not supported. at ProjA.MainClass.Main (System.String[] args) [0x00000] in <4f209fa43741462db3b8f73ac83c35a2>:0
Please note that this works fine for (+) operator or without the inline keyword.
1) Am I doing something wrong or is this a bug?
2) Is there any way to overcome this issue (but I need the inline keyword to make this function generic)?
3) Have you experienced something similar when calling f# function from c#, how did you solve it?
I'm using Mono 4.8 on macOS Sierra.
F♯ (F-sharp; also known as fa dièse or fi) is the seventh semitone of the solfège.
JavaScript +_ operator: It is a combination of the variable with symbol underscore( _ ) and unary plus ( + ) operator, + operator converts the type of _ variable to Number type for further operation. Example: The variable “_” with string type is stored in variable “r” with “number” type.
In general, functions declared as inline
will not be usable (or will not work the same as from F#) from other languages. They are replaced at the call site as a feature of the F# compiler, which is not supported by C# and other CLR languages. This is a significant advantage of F# over these other languages.
However, there are some exceptions. It is possible to write F# inline functions which perform dispatch based on the runtime type, which is then usable from C# and other languages. Typically, these will not get the same IL when used from C# as they do from F# for certain types (the specific handlers for primitive types will not be handled). This is why (+)
works - you can see this in the code for the operator, where (+)
calls AdditionDynamic<(^T),(^U),(^V)> x y
. Note that (-)
is missing the runtime dispatched version, and is explicitly marked as [<NoDynamicInvocation>]
, which is why it fails to work from C#.
This is effectively the same limitation in C# that has caused people to request things like IArithmetic (*using Internet Archive since it's been hidden in Connect) for many years. F# works around this via statically resolved type parameters, but this is a feature specific to F#, and will not work from C# and other languages. Wrapping the function through F# doesn't enable it in C#.
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