Reputation: 369
I have an existing project written in C#. I would like to move part of its business logic to F#. MyObjectX is a C# class that runs scientific algorithms. For MyObjectX to run it needs to implement a couple of interfaces, and some dependencies that are injected via methods (not constructor). Example:
public class MyObjectX(): IMathSolver, IBusinessSolver
{
//private fields
private int operationMode;
private ISignalProvider signal;
//Inject dependcy via method
public void SetSignalProvider(ISignalProvider signal)
{
this.signal = signal;
}
//implemention of above interfaces
public double MethodMathSolver()
{
this.signal.GetThreshold();
//...
}
public double Method1BusinessSolver()
{
}
public double Method2MathSolver(IResultProvider provider)
{
var x = provider.GetValueAtTime(0.1);
//...
}
}
So now I would like to implement MyObjectX in F#. What is the best way to do that so i can be as functional as possible in my code?
Make the existing C# MyObjectX behave as a wrapper/facade between the rest of C# classes and the F# library were the algorithms are implemented in F# modules.
Write a F# class of MyObjectX class that implements the interfaces, and probably call other F# modules.
Or non of them. please advise.
Also what is the best way to pass the dependencies of C# to F# like 'IResultProvider/ISignalProvider'? Do i need to use mutable variables that will get populated with the dependencies via functions in F#?
Please advise. if you can share a code sample i would be thankful.
Upvotes: 3
Views: 809
Reputation: 14478
I'd say go for (1).
That way, you'll have make your life easier referencing F# from other F# code, and the wrapper should be trivial to write. That will aslo add a level of indirection, letting you change the C# interface or the F# code without affecting the other side of the system.
Upvotes: 1
Reputation: 233505
FWIW, the (more or less) direct translation of MyObjectX
is
type MyObjectX() =
let mutable operationMode = 0
let mutable sp : ISignalProvider = Unchecked.defaultof<ISignalProvider>
member this.SetSignalProvider signal = sp <- signal
interface IMathSolver with
member this.MethodMathSolver () =
sp.GetThreshold()
//
0.0
member this.Method2MathSolver provider =
let x = provider.GetValueAtTime 0.1
//
x
interface IBusinessSolver with
member this.Method1BusinessSolver () = 0.0
although I had to guess at a couple of the interface definitions.
However, this isn't particularly functional. For more information about moving from an object-oriented to a functional mindset, see
Upvotes: 4
Reputation: 243096
I think you could choose between 1 and 2. These are certainly the two most reasonable approaches.
I think that the option 2 might be better, because the F# implementation can then stay in simple F# modules using the most idiomatic F# style (such as passing functions around as arguments). The idiomatic F# code is not always easy to use from C#, so if you wrap it in an F# class that implements the required C# interfaces, you are hiding the "F# details" from the C# code, which is good.
Have a look at:
F# Component Design Guidelines which says more things about how to design F# components in a way that makes them easy to use from C#.
Interfaces (F#) on MSDN and Interfaces page at F# for Fun and Profit for more details about how to actually write such interface implementation in F#.
Upvotes: 6
Reputation: 755587
So long as the interface is defined in an assembly referenced by the F# project you can just implement MyObjectX
directly
type MyObjectX(signal : ISignalProvider) =
let mutable operationMode : int = 0; // assuming this changes
interface IMathSolver with
member x.GetMethodMathSolver() : double =
signal.GetThreshold()
// ...
member x.MethodBusinessSolver() : double =
...
Upvotes: 2
Reputation: 3769
Take a look at the F# documentation. It is possible to create .NET classes and interfaces trivially and to use those within the language.
If you are looking to use IoC, you should have no problem injecting an F# implementation into a C# module and vice versa. Just have a play!
Upvotes: 1