Home > Enterprise >  How do I best capture possible side-effects of Func<..> in C#? Is there a best practice for th
How do I best capture possible side-effects of Func<..> in C#? Is there a best practice for th

Time:08-12

I have code from a maths library i am using, and cannot change. The function in question from the maths library I am using uses an approximation function iteratively, like this.

public double Calculate(double startInput, Func<double, double> approximationFunc)
{
    var result = 0d;
    var max = 10;
    for (int i = 0; i < max; i  )
    {
        result = approximationFunc(startInput);
        //do some checks ...
        startInput =DoSomething();
    }
    return result;
}

However, in the approximationFunc I am using 'in reality', I have to compute other things than the double result, and I need to re-use these results. The only thing I have come up with is:

 public void BusinessLogic(double startInput)
        {
            MyOtherResult myOtherResult = null;
            double myFunction(double input)
            {
                var result = ComputeMyResult(input);
                myOtherResult = ComputeMyOtherResult(result, someOtherStuff);
                return result;
            }

            var approximationResult = Calculate(startInput, myFunction);
            var myOtherApproximationResult = myOtherResult;
            // Do other stuff...
        }

However, I'm not sure if this the best way of getting the 'other result', and if there is a side-effects-free way of doing this. The solution I have come up with only works because I know that the library I use applies this function iteratively, and that's not ideal. How would you go about solving this in C#? I've been racking my brain for two days and it's not clicking.

CodePudding user response:

A delegate can (and usually does) have a target object. So: you can intentionally craft your target object as the state wrapper that you need for your logic. For example:

class MyState {
    public double MyFunc(double x) {
        // do whatever here, reading and writing to instance fields
        // on MyState
    }
}
...
var state = new MyState(/* additional values if needed */);
var result = ctx.Calculate(42, state.MyFunc);
  • Related