From: Sam Larbi Date: 2007-11-21T00:07:09+09:00 Subject: Re: using lambda, binding happens immediately? ------=_Part_6283_10698249.1195571222739 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit Content-Disposition: inline Thanks Robert, I have some more questions / responses below. On Nov 20, 2007 6:45 AM, Robert Klemme wrote: > 2007/11/19, Sam Larbi : > > I have this code: > > > > > > require 'test/unit' > > require 'leapyear' > > class LeapYearTest < Test::Unit::TestCase > > def setup > > @ly = LeapYear.new > > end > > def LeapYearTest.generate_tests > > filename = "testdata.dat" > > file = File.new(filename, "r") > > file.each_line do |line| > > year, is_leap = line.split; > > code = lambda { assert_equal(is_leap.downcase=="true", @ly.isleap > ?( > > year.to_i)) } > > define_method("test_isleap_" + year, code) > > end > > file.close > > end > > end > > > > > > What I want to know is why when I use define_method("name") {block;} > instead > > of define_method("name", lambda{block}) the binding seems to happen > later > > (after the each_line loop)? > > > > Is there a reason behind that? > > I'm not sure I understand you but why don't you just do > Well, the problem is that attaching the block uses only the last "year" to be processed in the loop, never the appropriate one. > > define_method("test_isleap_" + year) do > assert_equal(is_leap.downcase=="true", @ly.isleap?(year.to_i)) > end > My understanding is that this would do the same as define_method(...) { ...}, so I would expect to have the same problem. Basically, lets say the file testdata.dat has the following lines: 2000 true 2004 true 2001 false Then running the code above (with leapyear class defined as well) would use 2001 as the date for each of the tests if I used the block attachment as opposed to passing through the arguments after using lambda (although the tests would be named correctly). So basically, It would generate the following: test_isleap2000 -> but the date inside is 2001 test_isleap2004 -> but the date inside is 2001 test_isleap2001 -> the test is correct Then, if I use lambda, the tests are all correct. Does that make any more sense? > > Btw, I'd also use the block form of File.open because it is more > robust than the idiom you are using. > Thanks for pointing that out - I do like how it closes for you, so you don't have to remember to do it. Sammy Larbi ------=_Part_6283_10698249.1195571222739--