7

I am creating a simple DSL with multiple discriminated unions(DU) . There is building block DU and higher DUs are build on top of lower ones.

Now I want to create UI where user can build a text which matches my DSL. to UI I don't want to express my full grammar, but show only possible actions that can be done. So I need a way to figure out from my hierarchical DU, what are other possible states that user can do.

sample input text (1 + (2 * 3))

type Expression =
   | Constant of int
   | Add of Expression * Expression
   | Mul of expression * Expression

so when user starts, I have to return a list saying only Constant can be used. when user passes (constant ) as his current state, I have to tell you can add/Mul (which is expression) and so on.

I want to represent a structure which says, current state and possible states to go from in a type safe way. Is there a way to solve this kind of problem in f#

s952163
  • 6,276
  • 4
  • 23
  • 47
abhishek
  • 373
  • 1
  • 9
  • 1
    How do you define type-safe? Add / Mul requires two arguments. How do you represent those? – Asti Jan 10 '17 at 04:51
  • Can you expand your example? I'm not sure what is the case. – mjpolak Jan 10 '17 at 14:32
  • type reference means, if I am missing any state, I should get compile time error. If there are states (defined as Discriminated Union) and events to change state, is there a programmatic way to get list of all events (and if any event what possible state it can go to). – abhishek Jan 13 '17 at 01:18

1 Answers1

1

I think you're looking for FSharpType.GetUnionCases. You can use this as follows:

open System
open Microsoft.FSharp.Collections
open Microsoft.FSharp.Reflection

type Expression =
   | Constant of int
   | Add of Expression * Expression
   | Mul of Expression * Expression

typeof<Expression> |> FSharpType.GetUnionCases|> Dump |> ignore

LinqPad for the above here

Sean Kearon
  • 10,987
  • 13
  • 77
  • 93