Ben*_*hes 25
简单的答案是你不能,至少用MRI 1.8(标准).这是因为1.8通过遍历抽象语法树来工作.Python,Ruby 1.9,JRuby和Rubinius使用字节代码,允许编译为中间表示(字节代码).从MRI Ruby 2.3可以很容易地做到这一点,请参阅下面的答案.
使用Rubinius,您可以执行此帖中所述的操作:http://rubini.us/2011/03/17/running-ruby-with-no-ruby/
在JRuby中,你可以使用"Ahead Of Time"编译器,我相信,jrubyc.
这不是真正标准的做事方式,而且通常只是让你的Ruby实现像它想要的那样处理它.Rubinius至少会在第一次编译后缓存字节代码,并根据需要进行更新.
在2013年初,没有办法将Ruby转换为C/C++源代码然后进行编译.
但是,我听说Matz(Yukihiro Matsumoto)说研究人员正在日本创造这个工具.该项目应由日本政府建立.
否则你可以使用JRuby并用Java字节码编译它,或者你可以使用Rubinius.Rubinius在Rubinius VM的字节码(JIT编译器)中自动编译.可以将字节码中的Rubinius转换为LLVM IR,LLVM可以生成机器代码.
我知道这是一个老问题,但我发现了一个非常有趣的项目,可以为您的问题提供答案:http : //crystal-lang.org/
它基本上将 Ruby 编译为本地机器代码。这并不完全正确,因为 Crystal 不完全是 Ruby,您可能需要对代码进行一些修改。还有一些不支持的库(还),但对我来说,这一切看起来都非常有希望。
从ruby 2.3.0如此容易地将您的源代码编译为Ruby-VM可以理解的字节码。
byte_code = RubyVM::InstructionSequence.compile_file '/home/john/somefile.rb'
File.binwrite '/home/john/bytecode', byte_code.to_binary
Run Code Online (Sandbox Code Playgroud)
并在命令行中
$ cat bytecode
YARB?
IUsx86_64-linux*.*1
+1?!AA*1
!qy????????yyQ? E/home/john/somefile.rbE<main>E <class:A>EshivaEhelloEAEputsEcore#define_methodu????? 5M
Run Code Online (Sandbox Code Playgroud)
文件内容
class A
def shiva
puts 'hello'
end
end
Run Code Online (Sandbox Code Playgroud)
好吧,ruby需要花费一些时间将源代码编译为字节码,因此您可以将字节码直接加载到ruby中并执行。没有语法检查和编译的开销。它比正常过程快得多。
bytecode = File.readbin('/home/john/bytecode')
instruction_from_byte_code = RubyVM::InstructionSequence.load_from_binary byte_code
instruction_from_byte_code.eval
# => :shiva
Run Code Online (Sandbox Code Playgroud)
注意:此答案仅在MRI中测试。它可能会或可能不会在其他Ruby实现中起作用