From: "Ara.T.Howard" Date: 2004-02-25T07:54:50+09:00 Subject: Re: Need examples comparing Ruby to Python On Tue, 24 Feb 2004, David MacQuigg wrote: > I'm not seeing any fundamental advantage of Ruby blocks over Python > functions. there are no fundamental advantages of _any_ turing complete language over another correct? iff so this is kindof a moot statement. however there is a 'difference': blocks form closures, function calls do not: def callback; yield; end def a_callback? x; x = 42; end x = nil callback{ x = 42 } p x # => 42 x = nil a_callback? x p x # => nil > If your block is more than one line, or needs a print statement, just give > it a name and let it be a function. lambda's are used only for very short > blocks, where for example, you want to pass a simple function in an argument > list, but don't want to waste a line giving that function a name. technically speaking (see above) this is true. however, consider apis which have a massive proliferation of callbacks passed using blocks - say a gui api. writing a separate method for each button may be over kill and not lend itself to abstraction very well. there were a series of articles onlines recently where matz said something about concentrating on the human aspect of computing and that really rang true to me, what i mean is: would you rather see comment = %r/^\s*#/o empty = %r/^\s*$/o open(path).each do |line| next if line =~ emtpy or line =~ comment key, value = line.split(%r/=/o).map{|x| x.strip} opts[key] = value end or f = open(path) comment = %r/^\s*#/o empty = %r/^\s*$/o begin while((line = f.gets)) next if line =~ emtpy or line =~ comment parse_line line, opts end ensure f.close end # insert 1000 lines of source code here so pare_line is nice and tough to find def parse_line line, opts key, value = line.split(%r/=/o).map{|x| x.strip} opts[key] = value end doesn't matter? how about if there a 50 of them? 100? if there were a hundred of them would you rather see handlers = Hash[ :foobar => proc{|arg| p arg}, :barfoo => proc{|arg| raise arg}, :foo => proc{|arg| throw arg}, # 100 more... ] or # these are handlers - have fun naming all of them def foobar arg; p arg; end def barfoo arg; raise arg; end def foo arg; throw arg; end # 100 more... now say you actually had to pass 20 or so handlers to a method - how would you do this with functions? it would surely be uglier than: parse_config handlers obviously you could maintain a string list of all the handlers and keep it in sync with your definitions.... (sounds like a job for code generation - tedious!) see what i'm driving at: skipping around the source finding all those defs can be frustrating and lead to errors. the stack overhead is also higher - though that probably _really_ is moot! ;-) > I like Ruby's more compact |x| instead of Python's keyword - lambda x: - but > that is just my personal preference. that's as 'fundamental' as it gets with turing languages - look no further! ;-) truely - much research has been done to correlate a programmer's productivity with lines of code written - NOT with the type of code, in otherwords: 'compact' => 'advantage' and, i beleive, this relationship is some sort of exponential curve. cheers. -a -- =============================================================================== | EMAIL :: Ara [dot] T [dot] Howard [at] noaa [dot] gov | PHONE :: 303.497.6469 | ADDRESS :: E/GC2 325 Broadway, Boulder, CO 80305-3328 | URL :: http://www.ngdc.noaa.gov/stp/ | TRY :: for l in ruby perl;do $l -e "print \"\x3a\x2d\x29\x0a\"";done ===============================================================================