Consider the following piece of code:
scores |> Map.fold (fun state key value ->
state + (findCoefficient conversion.Coefficients key) * value)
0m
findCoefficient
returns a decimal, and scores
is a Map<string, decimal>
Now when I write this piece of code in Visual Studio, the F# Power Tools give me this lint suggestion/warning:
Lint: If no mutable arguments are partially applied in the chain of function calls, then the function calls and lambda could be replace with composition. e.g.
fun -> x |> isValid |> not
could be replaced withisValid >> not
How would I do this in this case?
This is a terrible advice from the linter, but it follows a valid reasoning.
I replace conversion.Coefficient
in your original snippet to make it a bit shorter:
scores |> Map.fold (fun state key value ->
state + (findCoefficient coeff key) * value) 0m
When you have a binary operator in F# such as a + b
, this can be rewritten as a function application (+) a b
- and so we can rewrite the above code as:
scores |> Map.fold (fun state key value ->
(+) state ((*) (findCoefficient coeff key) value)) 0m
Now, this is just a nested function application and so we can rewrite it with |>
:
scores |> Map.fold (fun state key value ->
value |> (*) (findCoefficient coeff key) |> (+) state) 0m
And now you can do what the linter suggests, which is to turn it into a function composition:
scores |> Map.fold (fun state key ->
(*) (findCoefficient coeff key) >> (+) state) 0m
This is not something I would ever want to write in practice, but you can see how the rules that the linter follows in other (reasonable) cases apply here. But I'd recommend opening an issue with the F# PowerTools suggesting that the linter should not give silly advice when the function involves binary operators :-).
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