// Standard pattern matching.
let Foo x =
match x with
| 1 ->
// ... lots of code, only evaluated if x == 1
| 2 ->
// ... lots of code, only evaluated if x == 2
// Standard pattern matching separated out, causing exception.
let Bar x =
let valueOne = //... lots of code, evaluated always. Exception if value <> 1.
let valueTwo = //... lots of code, evaluated always. Exception if value <> 2.
match x with
| 1 -> valueOne
| 2 -> valueTwo
In a pattern matching using "match", the code for each pattern can be large, see Foo above, making me want to split out the blocks as separate calls for improved readability.
The issue with this can be that the call will be evaluated even though the pattern is not matched, as in Bar above.
- Option 1: lazy eval.
- Option 2: forward the argument/parameters.
- Option 3: forward the argument/parameters and use Active pattern.
What is the preferred method for improving the readability where code under each pattern can be large. Or are there any other obvious solution to the problem?
// ===== OPTION 1 =====
// Pattern matching separated out, lazy eval.
let Foo x =
let valueOne = lazy //... lots of code, evaluated on Force().
let valueTwo = lazy //... lots of code, evaluated on Force().
match x with
| 1 -> valueOne.Force()
| 2 -> valueTwo.Force()
// ===== OPTION 2 =====
// Pattern matching separated out, with arguments.
let Foo x =
let valueOne a = //... lots of code.
let valueTwo a = //... lots of code.
match x with
| 1 -> valueOne x
| 2 -> valueTwo x
// ===== OPTION 3 =====
// Active Pattern matching separated out, with arguments.
let Foo x =
let (|ValueOne|_|) inp =
if inp = 1 then Some(...) else None
let (|ValueTwo|_|) inp =
if inp = 2 then Some(...) else None
match x with
| ValueOne a -> a
| ValueTwo b -> b
I would probably just extract the two bodies of the pattern matching into functions that take
unit
:This is similar to your solution using
lazy
, but as we are never re-using the result of the lazy value, there is really no reason for using lazy values - a function is simpler and it also delays the evaluation of the body.If you then find that there is some commonality between
caseOne
andcaseTwo
, you can again extract this into another function that both of them can call.