tags:

views:

88

answers:

2

Can anyone provide some clues as to why these two pieces of code are not equivalent? My only thought is that the .open in the latter code portion is not in a block and the file handle is left open.

File.open(file) do |io|
  io.each_line do |line|
    body_string << line
  end
end

and this one

File.open(file).each_line {|line| body_string << line}

Thanks.

+5  A: 

See IO class's API.

If File.open is given a block , it opens the file, executes the block, then closes the file.

If it is not given a block, it returns an object representing the file (just like File::new), so it might still be opened.

phtrivier
+3  A: 

File test.rb:

def test1
  body_string = []
  [ File.open(ARGV[0]).each_line { |line| body_string << line }, body_string ]
end
def test2
  body_string = []
  [ File.open(ARGV[0]) do |io|
    io.each_line { |line| body_string << line }
  end, body_string ]
end
puts(test1.inspect)
puts(test2.inspect)

File f:

hello!

output of ruby test.rb f:

[#<File:f>, ["hello!\n"]]
[#<File:f (closed)>, ["hello!\n"]]

The only difference is that, when File.open is given a block, it automatically closes the file handle.

HTH

Aidan Cully