7

This works quite nicely - just wondered if there are any improvements to shorten it ?

if (ARGV[0].nil?) then
    input=$<
else
    input=File.new(ARGV[0],"r");
end

...
# Do something with the input here, for example:
input.each_line do |line|
    puts line
end

3 Answers 3

18

You can eliminate the first five lines entirely.

From Pickaxe

$<: An object that provides access to the concatenation of the contents of all the files given as command-line arguments or $stdin (in the case where there are no arguments). $< supports methods similar to a File object: binmode, close, closed?, each, each_byte, each_line, eof, eof?, file, filename, fileno, getc, gets, lineno, lineno=, path, pos, pos=, read, readchar, readline, readlines, rewind, seek, skip, tell, to_a, to_i, to_io, to_s, along with the methods in Enumerable. The method file returns a File object for the file currently being read. This may change as $< reads through the files on the command line. [r/o]

Therefore:

print $<.read

Kernel.gets is shorthand for $<.gets, so:

while s = gets
  puts s
end
Sign up to request clarification or add additional context in comments.

3 Comments

Also, you can use ARGF, since it's an alias to $<.
yeah - that works great - it makes me wonder why I went round in circles the first time in order to catch this. I think it's possibly because of the slightly odd (but good) behaviour that you if run 'ruby myscript.rb' without args, that the script simply just exits - most programs (certaintly on Unix for instance) will sit and wait for stdin : so I guess I assumed that I had to implement something there - but in fact (thanks for the description) the Ruby interpreter does something quite useful and quite clever (as usual) there ! Thanks.
I'm right there with you. I'm still getting used to (and discovering) all of these little Ruby tricks.
3

Only ARGV ? works for me, "r" normally default so can skip it, and File.new() may be same to File(), So

input = ARGV ? $< : File.new(ARGV[0])

1 Comment

File("foo") no longer seems to work (ruby 2.3.1): NoMethodError: undefined method `File' for main:Object.
2

then and ; are optional

also you can use the ternary operator:

input = ARGV[0].nil? ? $< : File.new(ARGV[0],"r")

1 Comment

Great - +1 - but I voted the other answer as it is even shorter ! Good old Ruby !

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.