The design of quotations has changed quite a bit over last few release of F#. I recently updated the sample:

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
#light
open System.Collections.Generic
open Microsoft.FSharp.Quotations
open Microsoft.FSharp.Quotations.Patterns
open Microsoft.FSharp.Quotations.DerivedPatterns

let interpret exp =
    let operandsStack = new Stack<int>()    
    let preformOp f name =
        let x, y = operandsStack.Pop(), operandsStack.Pop()
        printf "%s %i, %i\r\n" name x y
        let result = f x y
        operandsStack.Push(result)
    let rec interpretInner exp =
        match exp with
        | SpecificCall <@ (*) @> (_,[l;r])      -> interpretInner l 
                                                   interpretInner r
                                                   preformOp (*) "Mult"
        | SpecificCall <@ (+) @> (_, [l;r])     -> interpretInner l 
                                                   interpretInner r
                                                   preformOp (+) "Add"
        | SpecificCall <@ (-) @> (_, [l;r])     -> interpretInner l 
                                                   interpretInner r
                                                   preformOp (-) "Sub"
        | SpecificCall <@ (/) @> (_, [l;r])     -> interpretInner l 
                                                   interpretInner r
                                                   preformOp (/) "Div"
        | Value (x,ty) when ty = typeof<int>    -> operandsStack.Push(x :?> int)
        | _ -> failwith "not a valid op"
    interpretInner exp
    printfn "Result: %i" (operandsStack.Pop())
    
interpret <@ (2 * (2 - 1)) / 2 @>

<int><int></int></int>

By on 1/4/2009 10:25 PM ()

Thanks Robert!

Beginner's question: I want to modify your code - to tell me what I need to add to your match statement to match things like <@ 5.0*x + 1.0 @>

For example, my attempt below prints "todo: handle Expr", but I want to see something like "todo: handle VariableReference"

| SpecificCall <@ (/) @> (_, [l;r]) -> interpretInner l
interpretInner r
preformOp (/) "Div"
| Value (x,ty) when ty = typeof<int> -> operandsStack.Push(x :?> int)
| x -> failwith ("todo: handle " + x.GetType().Name)

Thanks,
Jiri

By on 1/6/2009 2:52 PM ()
IntelliFactory Offices Copyright (c) 2011-2012 IntelliFactory. All rights reserved.
Home | Products | Consulting | Trainings | Blogs | Jobs | Contact Us | Terms of Use | Privacy Policy | Cookie Policy
Built with WebSharper