Macro to overload Base operators


#1

I wish to generate code like

Base.:(<)(a::∂ℝ{N},b::∂ℝ{N}) where{N} = <(a.x,b.x)

for all possible operators, and all sorts of combinations of input types. I need the “Base.” qualifier because I am in a module. I write a little code generator

for OP in (:(>),:(<),:(==),:(>=),:(<=),:(!=)) #...
   eval(quote
      $OP(a::∂ℝ{N},b::∂ℝ{N}) where{N} = $OP(a.x,b.x)
      $OP(a::ℝ    ,b::∂ℝ{N}) where{N} = $OP(a  ,b.x)
      $OP(a::∂ℝ{N},b::ℝ    ) where{N} = $OP(a.x,b  )
   end)
end

The problem I see is that my macro generates something like

<(a::∂ℝ{N},b::∂ℝ{N}) where{N} = <(a.x,b.x)

that is, my “Base.” qualifier is missing. I have tried to modify my metacode to do that, without success:

Base.:( $OP)(a::∂ℝ{N},b::∂ℝ{N}) where{N} = $OP(a.x,b.x)

does not do the trick. “LoadError: < not defined for…”

And I would like to add: same question in a macro, where I should replace OP with esc(OP) .


#2

Try to create a MWE (https://stackoverflow.com/help/mcve), something that is copy-paste-able. That usually gets more attention :slight_smile:


#3

Thanks Fredrike

Here we go: this code fails. To make it run, one must make the code to generate functio definitions qualified by “Base.”. But how?

Philippe

module    mymod
export    mytype

struct mytype
    x  :: Float64
end

macro Op1(OP)
    return quote
        $OP(a::mytype)  = mytype($OP(a.x)) # how to generate Base.OP, including macro hygiene?
    end
end
@Op1 cos
@Op1 sin
#...

for OP in (:(>),:(<),:(==),:(>=),:(<=),:(!=)) 
    eval(quote
        $OP(a::mytype,b::mytype) = $OP(a.x,b.x) # how to generate Base.OP
    end)
end

end # module

using mymod
a = mytype(1.)
b = mytype(2.)
@show a < b
@show cos(a)


#4

Use Base.$OP in your macro and in the eval


#5

Well that was silly.

Not the answer mind you, but that I did not try this!!!

:grinning:

Merci Cédric, ca marche maintenant!