[plt-scheme] redex: meta-function with alternatives

From: Eric Tanter (etanter at dcc.uchile.cl)
Date: Fri Sep 11 21:29:09 EDT 2009

Thanks Robby, that effectively does the job!

Just out of curiosity, this means lookup will always go fully in both  
branches, even when that would not really be needed (right?). Any  
simple way to avoid that?

Cheers,

-- Éric


On Sep 11, 2009, at 8:34 PM, Robby Findler wrote:

> I think you want something like this for the case with two options:
>
> (pick   ;; try that first
> (lookup os_2 f (store (l_3 os_3) ...))
>
> ;; if above fails (exception or #f) then try that:
> (lookup os_1 f (store (l_3 os_3) ...)))
>
> and then to use this pick metafunction:
>
> (define-metafunction foo
>  [(pick #f any) any]
>  [(pick any_1 any_2) any_1])
>
> hth,
> Robby
>
> On Fri, Sep 11, 2009 at 6:46 PM, Eric Tanter <etanter at dcc.uchile.cl>  
> wrote:
>> Hi,
>>
>> I want to define a simple recursive metafunction, but which has the
>> particularity of needing to somehow backtrack. It is doing a lookup  
>> in
>> terms, but some terms have two branches, and if the first one  
>> fails, it
>> should go in the second one.
>>
>> I see two options to do it:
>> - use exception handling (the "not found in first branch" case  
>> being caught
>> as a "no match for clause...")
>> - have a base case returns #f, and then somehow distinguish whether  
>> the
>> recursive call returned a normal term or #f, if normal term return  
>> it,
>> otherwise go through second branch.
>>
>> I actually can't figure out how to make either case work... I  
>> imagine the
>> latter solution is cleaner than exceptions, but couldn't make it  
>> work (with
>> term-let).
>>
>> This is a simplified version of what I have:
>>
>> (define-metafunction foo
>>  lookup : os f S -> any
>>  ;; lookup f in os
>>  ; os = (def f v)
>>  ((lookup (def f v) f (store (l os) ...)) v)
>>
>>  ; 'fail case'
>>  ((lookup (def f_1 v) f_2 (store (l os) ...)) #f
>>   (side-condition (not (eq? (term f_1) (term f_2)))))
>>
>>  ; os = (with os1 os2)
>>  ((lookup (with os_1 os_2) f (store (l_3 os_3) ...))
>>
>>    ;; try that first
>>     (lookup os_2 f (store (l_3 os_3) ...)
>>
>>    ;; if above fails (exception or #f) then try that:
>>     (lookup os_1 f (store (l_3 os_3) ...))
>> )
>>
>> any idea?
>>
>> Thanks in advance,
>>
>> -- Éric
>>
>>
>> _________________________________________________
>>  For list-related administrative tasks:
>>  http://list.cs.brown.edu/mailman/listinfo/plt-scheme
>>



Posted on the users mailing list.