Ruby double splat (**) operator cheatsheet
(Source/Credits: https://dev.to/ldrner/ruby-double-splat-operator-cheatsheet-5c8n)
The operator ** is useful as an options hash. def one_method(**options);end This form is comple...
The operator **
is useful as an options hash.
rb
def one_method(**options);end
This form is completely similar to the following:
rb
def another_method(options = {});end
In addition, you can strictly define the set of required keys for the method.
rb
def one_strict_method(first_name:, last_name: , **options)
puts "options: #{options}"
greeting = "Hello #{first_name} #{last_name}"
puts options[:upcase] ? greeting.upcase : greeting
end
```irb
pry(main)> one_strict_method(upcase: true)
ArgumentError: missing keywords: first_name, last_name
pry(main)> one_strict_method(first_name: 'John', last_name: 'Doe', upcase: true) options: {:upcase=>true} HELLO JOHN DOE => nil ```
Another advantage of double splat literal is that it works like #merge for Ruby Hash
```rb class Contact::ShowRepresenter #:nodoc: def call(contact) { contact: { base_info(contact), legal_info(contact), # You can add something more complex here. # **GeoLocaionRepresenter.new.(contact) } } end
private
def base_info(contact) { id: contact.id, first_name: contact.first_name, last_name: contact.last_name, email: contact.email, phone: contact.phone } end
def legal_info(contact) { legal_name: contact.legal_name, legal_type: contact.legal_type, mailing_address: contact.mailing_address } end end ```
irb
pry(main)>Contact::ShowRepresenter.new.(Contact.last)
=> {
:contact=>{
:id=>51986,
:first_name=>"Ilia",
:last_name=>"Kriachkov",
:email=>"ilia.kriachkov@jetrockets.ru",
:phone=>"+79000000000",
:legal_name=>"JetRockets",
:legal_type=>"LLC",
:mailing_address=>"15 Let Oktyabrya Street, #10b, Tver, Russian Federation 170008"
}
}
In conclusion, I want to demonstrate some benchmark results.
As you can see, the **
operator is a bit faster than Hash#merge.
```rb require 'benchmark' n = 50_000 Benchmark.bm(2) do |x| x.report('merge: ') { n.times { merge } } x.report('double_splat_merge:') { n.times { double_splat_merge } } end
def merge hash = { a: 'a' } { b: 'b' }.merge(hash) end
def double_splat_merge hash = { a: 'a' } { b: 'b', **hash } end ```
irb
user system total real
merge: 0.109247 0.088652 0.197899 ( 0.204470)
double_splat_merge: 0.079480 0.003590 0.083070 ( 0.083642)
Comments section
cescquintero
•May 1, 2024
Great article, thanks for sharing!