Overloading ()

Hi,

I was reading the comp.lang.functional group, and happened across a
little discussion of Ruby vs. Python on there.
One thing the Python guy asked was whether you could pass a function in
Ruby so that you could call it like:

f(args)

Which looks more like a real function call. And I must admit, that at
first, I was kind of put off at not being able
to pass functions around in Ruby and call them like normal functions
(I’ve since gotten used to the alternatives).
It got me thinking, why isn’t it possible to overload a () operator for
this purpose? Was it a design decision of
the language or does it just add too much of a hassle for the parser? Or
was it something else?

Not that I’m complaining or anything, since I don’t mind the way Ruby
does it. I’m just curious what the reasoning
was.

Thanks in advance.

  • Dan

You probably already know this, but you can call it like:

f[args]

which looks somewhat similar to a regular function call.

Nathaniel

<:((><

···

Dan Doel [mailto:djd15@po.cwru.edu] wrote:

I was reading the comp.lang.functional group, and happened across a
little discussion of Ruby vs. Python on there. One thing the Python
guy asked was whether you could pass a function in Ruby so that you
could call it like:

f(args)

Which looks more like a real function call.

Dan Doel wrote:

Hi,

I was reading the comp.lang.functional group, and happened across a
little discussion of Ruby vs. Python on there.
One thing the Python guy asked was whether you could pass a function in
Ruby so that you could call it like:

f(args)

Which looks more like a real function call. And I must admit, that at
first, I was kind of put off at not being able
to pass functions around in Ruby and call them like normal functions
(I’ve since gotten used to the alternatives).
It got me thinking, why isn’t it possible to overload a () operator for
this purpose? Was it a design decision of
the language or does it just add too much of a hassle for the parser? Or
was it something else?

Not that I’m complaining or anything, since I don’t mind the way Ruby
does it. I’m just curious what the reasoning
was.

Here’s one construction that becomes possible because () is not an operator:

def foo
3
end

foo = foo()
foo += 1
p foo # ==> 4

If () were an operator, the “foo()” syntax would have to be interpreted
as sending a #call message to the value of the local var “foo”.

I don’t know if that’s the main justification or a side effect, though.

Here’s one construction that becomes possible because () is not an
operator:

def foo
3
end

foo = foo()
foo += 1
p foo # ==> 4

If () were an operator, the “foo()” syntax would have to be
interpreted as sending a #call message to the value of the local var
“foo”.

I don’t know if that’s the main justification or a side effect, though.

Ah, that’s true. I hadn’t thought of that.

Seems like writing code like that is a bad idea, though, if you want to
be able to understand it in the future. :slight_smile:

  • Dan

BTW: That’s syntactic sugar for Proc#call. I recently had a problem with
this method while experimenting with CPS and current continuations. I
have used to call a Proc object and the program broke as I
wanted to drop in Continuation object in its place because the latter
only support the call method. Perhaps it would be a good idea to add
to Continuation to enable both to repsond to the same protocol?

···

On 2003-08-14 08:01:41 +0900, Nathaniel Talbott wrote:

You probably already know this, but you can call it like:

f[args]

which looks somewhat similar to a regular function call.


What country can preserve its liberties if its rulers are not warned from
time to time that their people preserve the spirit of resistance?
– Thomas Jefferson

Hi,

···

In message “Re: Overloading ()” on 03/08/14, Florian Frank flori@nixe.ping.de writes:

Perhaps it would be a good idea to add
to Continuation to enable both to repsond to the same protocol?

Nice idea. I will add it.

						matz.

“Yukihiro Matsumoto” matz@ruby-lang.org wrote in message
news:1060863609.376407.27138.nullmailer@picachu.netlab.jp…

Perhaps it would be a good idea to add
to Continuation to enable both to repsond to the same protocol?

Nice idea. I will add it.

Wow! Didn’t take much arm-twisting there, eh? =)

I’m the “Python guy” from comp.lang.functional. :wink: I’d still like to
understand why the () operator can’t be overloaded in Ruby, necessitating
the use of for Proc objects instead. What was the motivation behind that
restriction?

Thanks,
Dave

In article Q4Q_a.124$0u4.66@news1.central.cox.net,

···

Dave Benjamin dave@3dex.com wrote:

“Yukihiro Matsumoto” matz@ruby-lang.org wrote in message
news:1060863609.376407.27138.nullmailer@picachu.netlab.jp…

Perhaps it would be a good idea to add
to Continuation to enable both to repsond to the same protocol?

Nice idea. I will add it.

Wow! Didn’t take much arm-twisting there, eh? =)

I’m the “Python guy” from comp.lang.functional. :wink: I’d still like to
understand why the () operator can’t be overloaded in Ruby, necessitating
the use of for Proc objects instead. What was the motivation behind that
restriction?

I know you can overload () in C++, but can you overload () in Python?

Seems like allowing overloading of () is a potential tarpit… and there
are potential parser issues as well, but I defer to matz to answer your
question.

Phil

Hi,

I’m the “Python guy” from comp.lang.functional. :wink: I’d still like to
understand why the () operator can’t be overloaded in Ruby, necessitating
the use of for Proc objects instead. What was the motivation behind that
restriction?

Because you don’t always need parenthesises for method calls, for
example,

foo(1,2,3)
foo 1,2,3

obj.bar() # calling obj’s method bar
obj.bar # still calling bar (*)

The last line is very important difference from Python. Python gives
you the method object “bar”. It’s functional, but Ruby way allows
attribute abstraction.

In addition, Ruby has separate namespace for variables and methods,
for example,

def foo
puts 55
end
foo = 42
puts foo # “42”
puts foo() # “55”

This also makes () hard to be overloaded.
matz.

···

In message “Re: Overloading ()” on 03/08/15, “Dave Benjamin” dave@3dex.com writes:

Whenever someone says they would like to overload the () operator to
make procs look like functions, I like to point out …

(1) Ruby doesn’t have a () operator
(2) Ruby doesn’t have functions

Of course, that’s a bit of hand waving because certain method
invocations certainly do look a lot like function calls, and syntactic
sugar is always an option. But Matz has given a more definitive answer
elsewhere in this thread.

But … I’m wondering.

Is there some idiom that would be facilitated by overloading ()? The
only thing I can think of are C++ templates where the same bit of code
might cause f in “f()” to be bound to a function name at one invocation
or a functor object in another. Since Ruby doesn’t have C++ like
templates, this isn’t an issue.

I can’t think of other useful scenarios, but then I’m probably
insufficiently imaginative.

···

On Thu, 2003-08-14 at 14:10, Dave Benjamin wrote:

I’m the “Python guy” from comp.lang.functional. :wink: I’d still like to
understand why the () operator can’t be overloaded in Ruby, necessitating
the use of for Proc objects instead. What was the motivation behind that
restriction?


– Jim Weirich jweirich@one.net http://onestepback.org

“Beware of bugs in the above code; I have only proved it correct,
not tried it.” – Donald Knuth (in a memo to Peter van Emde Boas)

Because () isn’t really an operator – at least not yet, and I don’t know
whether or not Matz will make it an operator. I’m not sure whether I’d want
it to be an operator. Maybe Matz can make it so that the syntactic sugar
for Proc can work with () as well.

-austin

···

On Fri, 15 Aug 2003 03:10:21 +0900, Dave Benjamin wrote:

“Yukihiro Matsumoto” matz@ruby-lang.org wrote in message
news:1060863609.376407.27138.nullmailer@picachu.netlab.jp…

Perhaps it would be a good idea to add
to Continuation to enable both to repsond to the same protocol?
Nice idea. I will add it.
Wow! Didn’t take much arm-twisting there, eh? =)

I’m the “Python guy” from comp.lang.functional. :wink: I’d still like to
understand why the () operator can’t be overloaded in Ruby, necessitating
the use of for Proc objects instead. What was the motivation behind
that restriction?


austin ziegler * austin@halostatue.ca * Toronto, ON, Canada
software designer * pragmatic programmer * 2003.08.14
* 16.21.46

“Phil Tomson” ptkwt@aracnet.com wrote in message
news:bhgrv7013t@enews3.newsguy.com

I know you can overload () in C++, but can you overload () in Python?

Yes, it’s quite simple, actually:

class CallableClass:
def call(self):
print ‘Hey there!’

cc = CallableClass()
cc()

Output:
“Hey, there!”

Seems like allowing overloading of () is a potential tarpit… and there
are potential parser issues as well, but I defer to matz to answer your
question.

I won’t comment on whether the ability to overload () is good or bad,
necessarily (although it would be nice if Ruby’s lambdas had normal
functional semantics), but I would be very interested in understanding the
issue from a language design standpoint, if you’d be so kind, Matz.

Thanks!
Dave

The short answer is “no, I can’t think of any”. The longer answer
follows in the form of thinking out loud.

All callable objects in C++ respond to (). This includes function
objects, function pointers, and member function pointers.

All callable objects in Ruby repond to #call(). This includes Procs,
Methods, Continuations, and other objects. Many callable objects also
respond to # and #to_proc().

The same idioms apply in both cases; there is an object, and you want to
call it, but you don’t care what kind of object it is. In C++ you use
(), and in Ruby you use #call().

I can imagine one other situation in C++:

#include

struct Foo
{
void foo() { std::cout << “Foo::Foo()” << std::endl; }
};

struct Bar
{
struct Boo
{
void operator()() { std::cout << “Bar::Boo::operator()” << std::endl; }
};
Boo foo;
};

template
void foo(T t)
{
t.foo();
}

int main()
{
Foo f; foo(f);
Bar b; foo(b);
}

Here Foo and Bar both act like they have a member function foo(), but in
the case of Bar, it’s just a function object that responds to ().

With a little bit of black magic, I can do this in Ruby without
overloading ():

class Foo
def foo; puts “Foo#foo”; end
end

class Bar
class Boo
def call; puts “Bar::Boo#call”; end
end
def initialize
@b = Boo.new
p = proc { @b.call() }
m = Module.new
m.instance_eval do
define_method(:foo, p)
end
self.extend(m)
end
end

def foo(t)
t.foo()
end

f = Foo.new; foo(f)
b = Bar.new; foo(b)

It’s all a matter of creating an object that responds to the agreed-upon
protocol. C++ needs to be able to overload () for
backward-compatibility with C, because function pointers are not
first-class objects and can’t have member functions. In Ruby there is
no such requirement.

Paul

···

On Fri, Aug 15, 2003 at 08:21:25PM +0900, Jim Weirich wrote:

But … I’m wondering.

Is there some idiom that would be facilitated by overloading ()? The
only thing I can think of are C++ templates where the same bit of code
might cause f in “f()” to be bound to a function name at one invocation
or a functor object in another. Since Ruby doesn’t have C++ like
templates, this isn’t an issue.

I can’t think of other useful scenarios, but then I’m probably
insufficiently imaginative.

“Austin Ziegler” austin@halostatue.ca wrote in message
news:2003814162351.292849@PADD…

Because () isn’t really an operator – at least not yet, and I don’t know
whether or not Matz will make it an operator. I’m not sure whether I’d
want
it to be an operator. Maybe Matz can make it so that the syntactic
sugar
for Proc can work with () as well.

I think I’m really asking the wrong question here. What I’d really like to
know about is “callable objects”. The () is a syntactical construct that has
a different meaning in Ruby than in Python. In Ruby, () is optional. But
this isn’t what I’m really asking. I’m asking how one might make an object
in Ruby behave like a method.

irb(main):001:0> f = lambda {|x| x + 1}
=> #Proc:0x4022f524
irb(main):002:0> f 5
NameError: undefined method `f’ for #Object:0x4024dce0
from (irb):2
irb(main):003:0> f.call 5
=> 6

I understand that everything lives inside an object, so there are no free
functions, but there are certainly methods that behave like free functions;
I can create one of those things using “def”. What I can’t seem to do is
pass that method around and still call it without referencing the object
it’s attached to. Or can I?

Thanks everyone for the replies,
Dave

I will comment that although being able to overload () in ruby could make it
more consistent, it wouldn’t exactly give it totally normal functional syntax.
Since in ruby you can call functions like:

fun a, b, c

Without parentheses at all. Detecting such a case might be even more difficult
than the () case (I don’t really know), which might be why it’s not implemented
(is it better to have half of normal syntax, or none at all?).

Changing objects to automatically respond to a call method in the above case
would be qutie interesting, though, since you could actually curry functions in
that case, writing

fun a b c

Assuming it binds in the correct order. Currently currying looks like

fun[a][b][c], or with function syntax fun(a)(b)(c), which is somewhat cryptic.

If one is supporting callable objects, one might also look at the expression:

foo.a()

and say, “Does foo.a represent a method call, or does foo.a represent the
method object on which the () operator is being used?” In other words, should
ruby support:

fun_obj = foo.a
fun_obj()

Or should it stay with:

fun_obj = foo.method(:a)

?

The former requires that all methods be called with () in order to get the value
which I think would upset a lot of people, since it destroys accessors that
ruby has (i.e. foo.a is an accessor for the @a instance variable, but foo.a
looks like you’re simply accessing a public variable). The first scheme
supports more transparent first-class functions, but it comes at a big cost.

So, as you can see, implementing an overloadable () is a big can of worms.
There’s no immediate way to tell if foo() is a direct function call or a
callable object, or in bar.a(), whether a() is a function call, or whether
a is a function that returns a callable object that is being called (which
it probably wouldn’t be).

So, letting you overload () is of debatable value at best. It would at the very
least make things much more complex.

Food for thought.

  • Dan
···

“Dave Benjamin” dave@3dex.com wrote

I know you can overload () in C++, but can you overload () in Python?

Yes, it’s quite simple, actually:

class CallableClass:
def call(self):
print ‘Hey there!’

cc = CallableClass()
cc()

Output:
“Hey, there!”

Seems like allowing overloading of () is a potential tarpit… and there
are potential parser issues as well, but I defer to matz to answer your
question.

I won’t comment on whether the ability to overload () is good or bad,
necessarily (although it would be nice if Ruby’s lambdas had normal
functional semantics), but I would be very interested in understanding the
issue from a language design standpoint, if you’d be so kind, Matz.

Dave Benjamin wrote:

I understand that everything lives inside an object, so there are no free

functions, but there are certainly methods that behave like free functions;
I can create one of those things using “def”. What I can’t seem to do is
pass that method around and still call it without referencing the object
it’s attached to. Or can I?

You can’t, as far as I know.

Using def outside of a class doesn’t really create a free function
object. It creates a method in the current
class/module context (not sure what that is. Kernel?). So the reason you
can do

def foo; end

foo()

Is because you’re calling a method, not using a callable object. The
callable object would be accessible via

method(:foo)

Which gets the method bound to the symbol foo from the current
class/module context. So you’d do

m = method(:foo)
m

The big controversy is that if you allow callable objects with normal
method calling semantics, what does m contain in:

m = foo.a

Is m the result of calling the #a method of foo? Or is it the #a method
of foo itself? If you don’t allow callable
objects with normal method calling conventions, you don’t run into this
debate.

Also, for a more complex argument, how do you treat:

m = foo.a b c

? Does foo.a return a callable object to which you pass b and c as
arguments, or do you pass b and c to a?
If the latter is the behavior, but you want the former, you’d need

m = foo.a() b c

Which looks weird.

So having callable objects with normal method calling syntax makes
things a lot more complicated, which is,
I imagine why ruby doesn’t have them. Calling methods of an object
doesn’t directly use the method objects,
at least as far as the code is concerned.

Hope this helps some.

  • Dan

Dave Benjamin wrote:
erstand that everything lives inside an object, so there are no free

functions, but there are certainly methods that behave like free functions;
I can create one of those things using “def”. What I can’t seem to do is
pass that method around and still call it without referencing the object
it’s attached to. Or can I?

Is this what you are looking for?

class X
def x
p “X”
end
end

unbound = X.instance_method( :x )
x = X.new
bound = unbound.bind( x )
bound.call

or

bound = x.method( :x )
bound.call

···


([ Kent Dahl ]/)_ ~ [ http://www.pvv.org/~kentda/ ]/~
))_student_/(( _d L b_/ (pre-) Master of Science in Technology )
( __õ|õ// ) )Industrial economics and technological management(
_
/ö____/ (_engineering.discipline=Computer::Technology)

That’s something I’d been wondering – it came as a surprise to me that
all methods aren’t first-class objects. Of course, I was used to
needing to pass method handles around from all my time spent in PHP, and
since using Ruby, haven’t needed that even once.

I think the biggest thing is that methods-as-objects, or lambdas as
objects are a functional programming artifact, which doesn’t mesh with
OO very well at times. I think this is one of those cases.

Ari

···

On Fri, 2003-08-15 at 16:54, Dave Benjamin wrote:

“Austin Ziegler” austin@halostatue.ca wrote in message
news:2003814162351.292849@PADD…

Because () isn’t really an operator – at least not yet, and I don’t know
whether or not Matz will make it an operator. I’m not sure whether I’d
want
it to be an operator. Maybe Matz can make it so that the syntactic
sugar
for Proc can work with () as well.

I think I’m really asking the wrong question here. What I’d really like to
know about is “callable objects”. The () is a syntactical construct that has
a different meaning in Ruby than in Python. In Ruby, () is optional. But
this isn’t what I’m really asking. I’m asking how one might make an object
in Ruby behave like a method.

I think I’m really asking the wrong question here. What I’d really like to
know about is “callable objects”. The () is a syntactical construct that has
a different meaning in Ruby than in Python. In Ruby, () is optional. But
this isn’t what I’m really asking. I’m asking how one might make an object
in Ruby behave like a method.

irb(main):001:0> f = lambda {|x| x + 1}
=> #Proc:0x4022f524
irb(main):002:0> f 5
NameError: undefined method `f’ for #Object:0x4024dce0
from (irb):2
irb(main):003:0> f.call 5
=> 6

Well, you can convert your lambda into a method:

f = lambda {|x| x + 1}
class << self; self; end.instance_eval { define_method(:f,f) }
f(5)

prints 6

(from http://www.rubygarden.org/ruby?SingletonTutorial )

I understand that everything lives inside an object, so there are no free
functions, but there are certainly methods that behave like free functions;
I can create one of those things using “def”. What I can’t seem to do is
pass that method around and still call it without referencing the object
it’s attached to. Or can I?

You can create a ‘Method’ object and pass it around:

def hello(x)
puts “Hello #{x}”
end
m = method(:hello) # this is self.method(:hello)

m.call(“world!”)
m[“everyone”]

m is a first-class object and can be passed around.

However, (1) m is still implicitly bound to an object (‘self’ in this case),
even though you don’t explicitly reference it in the call; and (2) you have
to use one of the indirect call syntaxes to invoke it.

I think it’s more commonly used with an explicit object:

class X
def hello(x)
puts “Hello #{x}”
end
end
obj = X.new
meth = obj.method(:hello)

meth.call(“world!”)

These days I almost never write a program with a ‘def’ at the top-level. I
just wrap the whole lot in a class, and then stick MyClass.new.run (or
whatever) at the end of the program. It just makes things much tidier and
easier to reuse components.

Regards,

Brian.

···

On Sat, Aug 16, 2003 at 07:54:08AM +0900, Dave Benjamin wrote:

Aredridel wrote:

That’s something I’d been wondering – it came as a surprise to me that

all methods aren’t first-class objects. Of course, I was used to
needing to pass method handles around from all my time spent in PHP, and
since using Ruby, haven’t needed that even once.

I think the biggest thing is that methods-as-objects, or lambdas as
objects are a functional programming artifact, which doesn’t mesh with
OO very well at times. I think this is one of those cases.

I suppose that depends what you mean. Technically methods are first
class in Ruby because you can
pass them around as objects. Blocks are first class as well when
converted to Proc objects, and they
serve the same functions as lambda constructs in functional languages.

I agree with what you’re saying, though. Methods don’t exactly “feel”
first class in Ruby, since you need
to call #method to get the object, and you can’t use those objects
interchangably with method calls. It
works better this way within the context of Ruby, but it seems very
different when comparing it to a
pure functional language like, say, Haskell. It’s somewhat unfortunate
that it’s difficult to get certain
very useful concepts to mesh together perfectly, but I suppose that’s
just the way things are.

  • Dan