What's the practical use of *(1), &(2) , |(3), xor(4)?


Base.operators.jl contains the following definitions

*(x::Number) = x
(&)(x::Integer) = x
(|)(x::Integer) = x
xor(x::Integer) = x

The practical use of those functions is beyond my imagination. What would be examples of the usefulness of those functions?


Look at the code right below that definition (afoldl).


I see

afoldl(op,a) = a
afoldl(op,a,b) = op(a,b)
afoldl(op,a,b,c...) = afoldl(op, op(a,b), c...)

First statement

afoldl( &, 2 ) = 2
(&)(x::Integer) = x  # this definition is  not needed.

Second statement

afoldl( op, a, b ) = op( a, b )
afoldl( &, 2, 6 ) = (&)( 2, 6 ) # same as 2 & 6
(&)(x::Integer) = x  # this definition is  still not needed.

Therefore I’m still wondering: what’s the practical use of (&)(x::Integer) = x

Update: I didn’t look far enough.

 ($op)(a, b, c, xs...) = afoldl($op, ($op)(($op)(a,b),c), xs...)

# which may reduce to 
afoldl( ($op)(z) )


 ($op)(a, b, c, xs...) = afoldl($op, ($op)(a,b), c, xs...)

# would reduce no further than 
afoldl( ($op)(x, y) )

# which becomes the binary function call

Thus avoiding the need for a unary function.
But as I note further below, the current implementation is what it is. No point changing it.


What else would these operations mean? It’s standard in mathematics that a product of one item is equal to that item. The only reason the product of zero items isn’t defined in Julia is that without any arguments one doesn’t know what type of 1 to return.


Does this definition have any implications for the idea of using &foo to mean something like Ref(foo)? Numbers don’t need to be scalarized since they’re already single-element iterators, but it would still mean having the same operator, with the same number of arguments, meaning two different things based on its argument type.


I personally would favor an implementation that throws an error when a binary operator is being used as a unary operator. I most likely made a mistake if I wrote an expression like xor(x). Implicitly converting a binary operator to a NOP operator seems somewhat arbitrary.

However, I don’t wish to belabor this point. It is what it is. I was just curious if the unary use of a binary operator has practical meaning. For example, I consider (-) to be a binary operator, but using it as a unary operator also makes sense because in that case it moves a number from one side of the number line to the other side. Example: (-)(-2)


That’s a good point although the syntax with and without parens are different, so technically no, but it would just be confusing since &x would mean something different than &(x). Maybe open an issue?