9 people like it.

Simple NumericLiteral example

You can use numeric literals, constant expressions and operator overloading to make your own arithmetics. Useful in DSL languages. With NumericLiterals, you can use any of Q, R, Z, I, N, G. Basic syntax: [Number][Letter] will forward the call to the type NumericLiteral[Letter] to FromInt32 [Number] (or FromInt64 or FromString...)

 1: 
 2: 
 3: 
 4: 
 5: 
 6: 
 7: 
 8: 
 9: 
10: 
11: 
12: 
13: 
14: 
15: 
16: 
17: 
18: 
19: 
20: 
21: 
22: 
23: 
24: 
25: 
26: 
27: 
28: 
29: 
30: 
31: 
32: 
33: 
34: 
35: 
36: 
37: 
38: 
39: 
40: 
41: 
42: 
43: 
44: 
45: 
46: 
47: 
48: 
//-----------------------------------------------------
//First example:

module NumericLiteralN =
    let FromZero() = ""
    let FromOne() = "n"
    let FromInt32 x = String.replicate x "n"

// Calls FromOne():
let x1 = 1N 
// val x1 : string = "n"

// Calls FromInt32(7):
let x2 = 7N
// val x1 : string = "nnnnnnn"

//Calls operator (+) on strings.
let x3 = 2N + 3N
// val x3 : string = "nnnnn"


//-----------------------------------------------------
//Second example:

type MyExpression =
| Const of int
| Plus of MyExpression * MyExpression
| Mult of MyExpression * MyExpression
with 
    static member (+) (x, y) = Plus(x,y)
    static member (*) (x, y) = Mult(x,y)

module NumericLiteralZ =
    let FromZero() = Const 0
    let FromOne() = Const 1
    let FromInt32 = Const

let rec eval tree =
    match tree with
    | Plus (x, y) -> eval x + eval y
    | Mult (x, y) -> eval x * eval y
    | Const x -> x

let expression = 3Z + (4Z * 5Z)
// val expression : MyExpression = Plus (Const 3,Mult (Const 4,Const 5))

let res = eval expression
// val res : int = 23
val FromZero : unit -> string

Full name: Script.NumericLiteralN.FromZero
val FromOne : unit -> string

Full name: Script.NumericLiteralN.FromOne
val FromInt32 : x:int -> string

Full name: Script.NumericLiteralN.FromInt32
val x : int
module String

from Microsoft.FSharp.Core
val replicate : count:int -> str:string -> string

Full name: Microsoft.FSharp.Core.String.replicate
val x1 : string

Full name: Script.x1
val x2 : string

Full name: Script.x2
val x3 : string

Full name: Script.x3
type MyExpression =
  | Const of int
  | Plus of MyExpression * MyExpression
  | Mult of MyExpression * MyExpression
  static member ( + ) : x:MyExpression * y:MyExpression -> MyExpression
  static member ( * ) : x:MyExpression * y:MyExpression -> MyExpression

Full name: Script.MyExpression
union case MyExpression.Const: int -> MyExpression
Multiple items
val int : value:'T -> int (requires member op_Explicit)

Full name: Microsoft.FSharp.Core.Operators.int

--------------------
type int = int32

Full name: Microsoft.FSharp.Core.int

--------------------
type int<'Measure> = int

Full name: Microsoft.FSharp.Core.int<_>
union case MyExpression.Plus: MyExpression * MyExpression -> MyExpression
union case MyExpression.Mult: MyExpression * MyExpression -> MyExpression
val x : MyExpression
val y : MyExpression
val FromZero : unit -> MyExpression

Full name: Script.NumericLiteralZ.FromZero
val FromOne : unit -> MyExpression

Full name: Script.NumericLiteralZ.FromOne
val FromInt32 : arg0:int -> MyExpression

Full name: Script.NumericLiteralZ.FromInt32
val eval : tree:MyExpression -> int

Full name: Script.eval
val tree : MyExpression
val expression : MyExpression

Full name: Script.expression
val res : int

Full name: Script.res
Raw view Test code New version

More information

Link:http://fssnip.net/bB
Posted:11 years ago
Author:Tuomas Hietanen
Tags: numericliteral , literal , dsl