Question

I want to create a type in F# that can have values of either "flag / enumeration types" a or b, or a float32 value between 0.0f and 1.0f inclusive. E.g.:

type mixedType =
    | a = -2.0f
    | b = -1.0f
    | [0.0f .. 1.0f]

The above code snippet is of course incorrect. Is there a way to create such a type?

My goal with mixedType is to reduce the number of variables passed to a function used in automated testing. Originally, I had 2 flags (aFlag : bool), (bFlag : bool) and (slidingValue : float32) displaying the following relationship:

  • if aFlag is true, then bFlag is false and the value of slidingValue is irrelevant
  • if aFlag is false, then
    • either bFlag is true and the value of slidingValue is irrelevant,
    • or bFlag is false and slidingValue can take up a float32 value between 0.0f and 1.0f inclusive and its value is used in my function.
Was it helpful?

Solution

You can create the type with:

type mixedType = A | B | Sliding of float32

then you convert the flags/float values to a value of this type with:

let getMixed af bf sliding = match (af, bf, sliding) with
    | (true, _, _) -> A
    | (false, true, _) -> B
    | (false, false, s) -> if s >= 0.0f && s <= 1.0f then Sliding(s) else failwith "Invalid sliding value" 

OTHER TIPS

Since you know the three cases you're interested in, maybe just make a type for those?

type TestCase = 
       A
     | B1
     | B0 of float32

Then to run the tests, you'd do, e.g.:

B0 0.66 |> run_tests

You'd implement your automated tests something like:

fun run_tests = function 
      A ->    (* Test with aFlag = true,  bFlag = false. *)
    | B1 ->   (* Test with aFlag = false, bFlag = true.  *)
    | B0 f -> (* Test with aFlag = false, bFlag = false, and using the value f. *)

I chose the names "B1" and "B0" to indicate whether or not bFlag is true or false. I'm sure that in your actual case, the semantics of the testcases/program will inspire better ones.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top