hoodwink.d enhanced
RSS
2.0
XHTML
1.0

RedHanded

Function Call #

by babie in inspect

Translated from matz blog, 2005-02-18:

There is no breathing space because I had a deadline for periodical article. On the rebound, I contemplated Ruby. I suppose that I’m filled with pleasure in this time.

Python emulates OOP by being based on Function and Record, but Ruby’s Function is an emulation based on OOP. Therefore it’s not cool when we call lambda.

We need the ”.call”.

    f = lambda{|x| p x}
    f.call(12)

I wanna write it like this.

    f = lambda{|x| p x}
    f(12)

On this new rule,

  • When the name of something like function is a local variable, it apply a “call” to the variable.

What do you think?

Actually, I tried it before, but I failed for:

  • I used the special method “()” instead of “call”.
  • I tried to support that “foo.bar(12)” means “foo.bar.().call(12)”.

The new way’s fault is that a method can’t called if a local variable has a same name. There is no matter usually, but there’s a case that it’s frequently duplicated like “p” method. Should I prepare the way to avoid?

said on 20 Feb 2005 at 12:16

I would love this. it seem a slight variation on the theme found here

said on 20 Feb 2005 at 12:32

I’ve wanted this for some time. I’ve found that the #call method is kind of embarrassing to explain to new Rubyists, because on one hand I say that Ruby supports first-class functions, and on the other hand I say that you can invoke them directly… This would be awesome.

said on 20 Feb 2005 at 15:27
I would love this too, but it seems to open ambiguities when dealing with functions that don’t take any parameters (and when you pass in arguments w/out the parans).

f = lambda{ "yea baybe" }
p f

Does the above ‘p’ operate on the function ‘f’ or the return value of function f? Or do we have to explicitly put the parans on the end like this to get the function called?

p f()

In which case, when can we leave off the parans? Only when dealing with local variables? Just functions, not methods, right? Ugh. Seems like ’.call’ is looking easier to deal with than all the new rules to remember. What about functions returned from a method?

class Klass
  attr_reader :f
  def initialize
    f = lambda{ "yea baybe" }
  end
  def m
    "yea baybe" 
  end
end

o = Klass.new
p o.m            # => "yea baybe" 
p o.f.call       # => "yea baybe" 

# Now using the new idea, can we do this?
p o.f()          # => Does this work?
p o.f            # => does this return the function or the return value of the function?
p o.method(:m)   # and this?
p o.method(:m)() # ???

More questions!!
f = lambda{ lambda{|i| p i} }
f(3)   # who gets the '3' argument?

Ok, enough! I’d love to see this work, too. But I hope we can work out all the little twists it might introduce.
said on 20 Feb 2005 at 16:36

Personally, I’m happy with the f[3] syntax.

This seems too magic…

said on 20 Feb 2005 at 17:03

I like it. I especially like the idea that Matz tried this before and couldn’t reconcile the behavior. It’s satisfying to revisit an idea and find a simpler answer. Read that first paragraph and sense his elation. It’s cool. Go for it.

said on 20 Feb 2005 at 17:32

Gab, 1.9 procs can take blocks.

said on 20 Feb 2005 at 17:41

Dan, here are the answers:

f = lambda{ "yea baybe" }
p f   # no call happen without parens

p f() # execute f.call due to explicite parens

p o.f()          # 'o.f' is not a local variable
p o.f            # this returns the function
p o.method(:m)   # plain method object
p o.method(:m)() # 'o.method(:m)' is not a local variable

f = lambda{ lambda{|i| p i} }
f(3)   # who gets the '3' argument?
# outer lambda, and since it does not take argument,
# error will be raised.
said on 20 Feb 2005 at 18:05

Personally I would be against this. To be honest, I don’t find myself using .call an extreme amount. I do however, call tons of methods without using brackets, ala x = y.z. In my opinion you would be sacrificing a commonly used convience for a small teaspoon of syntactical sugar.

Of course, that’s just what I think (And perhaps I’ve misunderstood you)—it’s your language, and a beautiful one, I might add, so do as you see fit!

said on 20 Feb 2005 at 18:21

Wow. Talk about quick feedback (and from the source!). Thanks, matz!

I understand now. Essentially only local variables that refer to a function will feel the change. Parans are necessary for the call to be made. Gotcha.

Although it would be nice for all variables that refer to a function to be treated this new way. It too much to ask, I know :( Oh, yea, and allowing objects to define a ‘()’ operator…whoops, didn’t say it. Move along.

said on 21 Feb 2005 at 00:08

you can0t see me but I’m dancing the mud monkey dance, whatever that is :)

said on 21 Feb 2005 at 00:59

the mud monkey dance? isn’t that just the roger rabbit except you fly out of a saxophone and land in the year 2121? no wonder i can’t see you.

said on 21 Feb 2005 at 06:31

Names flying here… :) greetz @ matz + why j/k… :))

said on 22 Feb 2005 at 09:47

Dan, I’m afraid that your prefered way is python/scheme way after all, which I don’t want.

said on 22 Feb 2005 at 15:07

I like the parens-optional normal syntax and don’t mind the mandatory parens for this purpose. It’s much better than #call, anyway.

But can we override operator()? :)

said on 22 Feb 2005 at 18:06

I don’t strongly oppose this, but I really don’t see why it’s necessary. Are there any situations where this would really make a large difference?

said on 23 Feb 2005 at 09:51

What if you invert this?

f = lambda{|z| z.y}

produces a callable object. def g ; end does, but it doesn’t return a Method object, it just makes g callable. Maybe allow ::f and ::g to refer to the objects and f and g be calls with no args? Then you can have ::f() be a call with no args, also. We have a convention, but not enforced that :: is used in the construction of paths to objects and Class.x or instance.x is a call to a method.

Present whitespace rules mean that x.y is x .y and is x. y, otherwise we could have .x as the explicit method call syntax. Actually, it seems that the same whitespace rules apply to :: as to . Interesting.

Final thought: would .do be [50%] better than .call?

said on 17 Jun 2005 at 04:12

As some others, I’m really wondering why you would want this. What is the problem about call? And if you really implement calling procs with parentheses, what is the essential difference between procs and methods now?

Comments are closed for this entry.