Explanation of macros; Haskell macros
Dirk Thierbach
dthierbach at gmx.de
Fri Oct 31 02:24:11 EST 2003
Coby Beck <cbeck at mercury.bc.ca> wrote:
>
> "Pascal Costanza" <costanza at web.de> wrote in message
> news:bnscfb$p1k$1 at newsreader2.netcologne.de...
>>
>> I had several cond statements at various places of my code. They
>> all didn't have a default case. At a certain stage, I needed to be
>> sure to get an exceptional return value for the default case
>> instead of NIL. So I added a macro:
Since the overhead of evaluating it at runtime is minimal, especially
with lazyness, that's exactly the situation where it is natural to use
a HOF instead of a macro.
I didn't go through the two proposed Lisp solutions in detail, but here's
a HOF in Haskell that does the same. First a general 'cond' with an
explicit default case, then 'econd' based on cond with an error as
default case:
cond :: a -> [(Bool, a)] -> a
cond def [] = def
cond def ((True,x):_) = x
cond def ((False,_):xs) = econd xs
econd :: [(Bool, a)] -> a
econd = cond (error "Default econd case")
> CL-USER 91 > (econd
> ((= 3 4) "foo")
> ((= 4 4) "bar"))
> "bar"
>
> CL-USER 92 > (econd
> ((= 3 4) "foo")
> ((= 4 5) "bar"))
>
> Error: fell through ECOND form.
GHC Interactive, version 5.02.2, for Haskell 98.
Main> econd [(3 == 4, "foo"), (4 == 4, "bar")]
"bar"
Main> econd [(3 == 4, "foo"), (4 == 5, "bar")]
*** Exception: Default econd case
I have made the recursion of 'cond' explicit, but of course 'cond' can
be defined by a fold (and partial application):
cond' = foldr (\(guard,val) def -> if guard then val else def)
You DON'T need macros for such things. You don't need dynamic typing,
either.
- Dirk
More information about the Python-list
mailing list