3 ms·
> its just syntax sugar for a symbol passed to a #send call This isn't the case. If you override `send` it only affects direct usage of `send`. You can't overr
by djur 4y ago
> its just syntax sugar for a symbol passed to a #send call
This isn't the case. If you override `send` it only affects direct usage of `send`. You can't override method dispatch. You can in some other OO languages but not Ruby.
Agreed otherwise. `x.foo` in Python and `x.method(:foo)` in Ruby do the exact same thing -- return a bound method object that can be called. These are both "proxies" in a sense but they're also first-class functions in all meaningful senses.
- dragonwriter 4y ago> This isn't the case. If you override `send` it only affects direct usage of `send`. Correct, I both (minor) confused #send with #__send__ and (more signifcant) misremembered the mechanism of some deep metaprogramming hacks involving a a mostly blank proxy object and #method_missing as using metaclasses and #send/#__send__ hacking; where that came from I don’t know. Should have not mentioned overriding (as its a tangent, in any case, as well as vmbeung wrong) or the #send method and referred to the fundamental underlying message send operation.
- empthought 4y agoYou just gave away the difference right there. x.foo doesn’t “return a bound method object.” It just accesses an attribute and returns the value of that attribute. The attribute can be any Python value. If it’s a callable then it can be called with parens. There is no proxying whatsoever. In contrast x.method(:foo) does do that proxy construction that you describe… because Ruby does not have first-class functions.
- djur 4y ago> x.foo doesn’t “return a bound method object.” It just accesses an attribute and returns the value of that attribute. The attribute can be any Python value. Python docs, section 3.2, subsection "Callable types". https://docs.python.org/3/reference/datamodel.html#the-standard-type-hierarchy https://docs.python.org/3/reference/datamodel.html#the-stand... x.foo returns an "instance method object", which is a "callable type". Also referred to as a "bound method", the same term that Ruby and JavaScript use. > When an instance method object is called, the underlying function (__func__) is called, inserting the class instance (__self__) in front of the argument list. For instance, when C is a class which contains a definition for a function f(), and x is an instance of C, calling x.f(1) is equivalent to calling C.f(x, 1)... Note that the transformation from function object to instance method object happens each time the attribute is retrieved from the instance... It is also important to note that user-defined functions which are attributes of a class instance are not converted to bound methods; this only happens when the function is an attribute of the class. This last part is why the following program has an error: def foo(self): print(self) class Foo: def __init__(self, fn): self.foo = fn x = Foo(foo) x.foo()
- empthought 4y agoYou are studiously missing the point and spamming irrelevant details. Yes, there's a Python "proxy" in your docs but it is syntactically transparent. Proc's proxy is not transparent. me: > If it's a callable then it can be called with parens The docs: > These are the types to which the function call operation (see section Calls) can be applied: True of Python instance method objects. False of Ruby Methods and Procs. Therefore Python has first-class methods, and Ruby does not have first-class functions nor first-class methods. End of discussion.
- djur 4y agoIn Ruby, the function call operator, `.()`, can be used on both Method and Proc objects. This being different from the syntax used for method invocation does not have anything whatsoever to do with whether functions are first class. You are both wrong and being unreasonably rude about it.