以下是我在晦涩的Ruby系列中发现的一些东西.
因此,在Ruby中,Unix命令的一个简单的no-bells实现cat
将是:
#!/usr/bin/env ruby puts ARGF.read
ARGF
在输入方面是你的朋友; 它是一个虚拟文件,从命名文件或STDIN中获取所有输入.
ARGF.each_with_index do |line, idx| print ARGF.filename, ":", idx, ";", line end # print all the lines in every file passed via command line that contains login ARGF.each do |line| puts line if line =~ /login/ end
谢天谢地,我们没有得到Ruby中的钻石操作符,但我们确实得到ARGF
了替代品.虽然模糊不清,但它实际上证明是有用的.考虑一下这个程序,该程序-i
在命令行中提到的每个文件上就地存在版权标题(感谢另一个Perlism ):
#!/usr/bin/env ruby -i Header = DATA.read ARGF.each_line do |e| puts Header if ARGF.pos - e.length == 0 puts e end __END__ #-- # Copyright (C) 2007 Fancypants, Inc. #++
归功于:
http://www.oreillynet.com/ruby/blog/2007/04/trivial_scripting_with_ruby.html#comment-565558
http://blog.nicksieger.com/articles/2007/10/06/obscure-and-ugly-perlisms-in-ruby
Ruby提供了另一种处理STDIN的方法:-n标志.它将整个程序视为在STDIN上的循环中(包括作为命令行args传递的文件).请参阅以下1行脚本:
#!/usr/bin/env ruby -n #example.rb puts "hello: #{$_}" #prepend 'hello:' to each line from STDIN #these will all work: # ./example.rb < input.txt # cat input.txt | ./example.rb # ./example.rb input.txt
我不太确定你需要什么,但我会用这样的东西:
#!/usr/bin/env ruby until ARGV.empty? do puts "From arguments: #{ARGV.shift}" end while a = gets puts "From stdin: #{a}" end
请注意,因为ARGV数组在第一次之前是空的gets
,所以Ruby不会尝试将参数解释为从中读取的文本文件(从Perl继承的行为).
如果stdin为空或没有参数,则不打印任何内容.
几个测试用例:
$ cat input.txt | ./myprog.rb From stdin: line 1 From stdin: line 2 $ ./myprog.rb arg1 arg2 arg3 From arguments: arg1 From arguments: arg2 From arguments: arg3 hi! From stdin: hi!
也许这样的事情?
#/usr/bin/env ruby if $stdin.tty? ARGV.each do |file| puts "do something with this file: #{file}" end else $stdin.each_line do |line| puts "do something with this line: #{line}" end end
例:
> cat input.txt | ./myprog.rb do something with this line: this do something with this line: is do something with this line: a do something with this line: test > ./myprog.rb < input.txt do something with this line: this do something with this line: is do something with this line: a do something with this line: test > ./myprog.rb arg1 arg2 arg3 do something with this file: arg1 do something with this file: arg2 do something with this file: arg3
while STDIN.gets puts $_ end while ARGF.gets puts $_ end
这是受Perl的启发:
while(){ print "$_\n" }