How to compile Ruby?

From ruby 2.3.0 its so easy to compile your source code to bytecodes that the Ruby-VM understands.

byte_code = RubyVM::InstructionSequence.compile_file '/home/john/somefile.rb'

File.binwrite '/home/john/bytecode', byte_code.to_binary

and in Command Line

$ 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

The content of the file

class A
  def shiva
    puts 'hello'
  end
end

What is the purpose?

Well, ruby takes time to compile your source code into byte codes so you can load your bytecodes directly into ruby and execute. No overhead of grammar checking and compilation. It much faster than normal processes.

How to load byte code?

bytecode = File.binread('/home/john/bytecode')
instruction_from_byte_code = RubyVM::InstructionSequence.load_from_binary bytecode

instruction_from_byte_code.eval
# => :shiva

Note: This answer is tested in MRI only. It might or might not work in other Ruby Implementations


The simple answer is that you can't, at least with MRI 1.8 (the standard). This is because 1.8 works by walking the Abstract Syntax Tree. Python, Ruby 1.9, JRuby, and Rubinius use byte code, which allows compilation to an Intermediate Representation (byte code). From MRI Ruby 2.3 it has become easy to do this, see this answer below.

With Rubinius, you can do something as described in this post: http://rubini.us/2011/03/17/running-ruby-with-no-ruby/

In JRuby you can use the "Ahead Of Time" compiler through, I believe, jrubyc.

This isn't really the standard way of doing things and you're generally better off just letting your Ruby implementation handle it like it wants to. Rubinius, at least, will cache byte code after the first compilation, updating it as it needs to.


I know this is an old question but I found a very interesting project that may provide an answer to your question: http://crystal-lang.org/

It basically compiles Ruby to native machine code. That's not exactly true because Crystal is not exactly Ruby and you might have to make some modifications to your code. There are also libraries that are not supported (yet) but to me it all looks very promising.