From: Csaba Henk Date: 2005-02-27T18:44:59+09:00 Subject: Re: A Ruby-relevant quote from Alan Kay On 2005-02-26, Steven Shaw wrote: > What is the threading problem? It looks ok to me... :-) In TrueModule #ifthen stores the block passed to it. #else is where the block is called actually. It's possible that between the calls to #ifthen and #else a call occurs to #ifthen in another thread, and the proper block gets overwritten. It's easy to get around this, though. module TrueModule def ifthen &b @blh ||= {} @blh[Thread.current] = b self end # rewrite other methods accordingly ... end I'm using this technique in a general multiblock framework (soon to be announced). > It's annoying that ifthen doesn't work when there is no else block and > that calling else directly on true fails but on false it works. Yes, of course, what I put together is quite rudimentary. And defining #when/#on_true and the counterpart methods is quite handy. > I didn't know about calling a block with [] rather than .call. That's > cool but I prefer .call for now. Neither about sending :include message > to classes - that's not something I would have thought of. That's the Tim Toady part of Ruby :). > I came up with some code to do the unless and when methods for single > argument versions of if and if not. I also came up with if_then a two > argument version where I simply pass in two blocks as normal arguments > (rather than as the implicit block argument). The result calling side > syntax is a bit ugly: > > result = 10.if_else Proc.new { > ... > }, Proc.new { > ... > }; > > It's starting to remind me of doing blocks/closures in Java (but not yet > *that* ugly). When Ruby get's keyword arguments it will look a little > better: > > result = 10.if Proc.new { > ... > }, else: Proc.new { > ... > }; Why to wait for "native" keyword arguments? And why not just "proc"? result = 10.if proc { ... }, :else => proc { ... }; is not uglier imho. If there is problem with the current sugared-hash-as-keyword-container approach, then that's not it's ugliness [I mean I don't think it's ugly], but the lack of reflection. These faked multiblocks can be used as a keyword mechanism with reflection. The only drawback is that you have to use some kind of finalizer method to express that there are no more components. Make that short, and it's liveable with. It's definitely better than writing out the procs. In the present case, we can tune the code to make foo.if{ ... }.fi foo.else{ ... } foo.if{ ... }.else{ ... } work (both with false/nil and the rest of the world), or, if we put more emphasis on syntactical consistency, we can rather have foo.else{ ... }.fi foo.if{ ... }.else{ ... }.fi for the latter two. > Then the 1-arg if and the 2-arg if-then-else can be done with a single > method without too much trouble. It would be nice to be able to elide > the Proc.new calls and have something like: > > result = 10.if { > ... > }, else: { > ... > }; I don't think the above would be essentially uglier. ".fi" is just three characters, it's not a perversion to think of it as a delimiter... > And seriously nice if you didn't have to use commas to separate > arguments when not using "()" style calling syntax. Hm, your code give me an idea. If ruby had real keyword args, we could allow the omission of "proc" for keyword arguments without breaking the present block semantics... that's interesting, as we couldn't introduce a general "omit proc in method argument" solution without either hacking the semantics of block arg passing, or putting syntactical cruft elsewhere, which is then quite beating the purpose. And... you don't even need proper keyword args for this. With the same logic, you could just let "proc" being omitted within hash literals. That is, make { 1 => {|i| i+1} } be the same as { 1 => proc{|i| i+1} } of current ruby... > Here's the modified code for the curious: Thanks! > > This latter thingy is what the Smalltalkers are proud of, ain't it? > > I'm not a proud Smalltalker. I think both Smalltalk and Ruby are great > (the Smalltalk image thing makes me uncomfortable though). I just wanted > to see the code 'cause I thought I'd learn something from it :-). I did > - thanks. I didn't imply you are a Smalltalker, be it a good or a bad thing (I'd guess it's the former). I spoke of Smalltalk(ers) in general. Maybe someone more involved with Smalltalk could then tell us whether she or he is proud of these properties of the Smalltalk conditional :) Cheers, Csaba