These two statements are incredibly dissimilar in almost every way.
If we were to find the equivalent ECMAScript code for this Ruby snippet:
-> { 10.times {|i| puts i} }.call
It might look something like this:
(() => { 10.times(i => puts(i)) }).call()
However, since numbers cannot have methods in ECMAScript, a solution similar to the following is necessary:
(() => { times(10, i => puts(i)) }).call()
To make this work, we would need to include some extra Ruby library support code:
(() => { times(10, i => puts(i)) }).call()
function times(i, f) { if (i-- === 0) return; else { times(i, f); f(i) }}
function puts(s) { console.log(s) }
While still not identical to the original Ruby behavior, it's much closer compared to the alternative proposal:
- Your approach introduces
i
into the global scope, whereas the Ruby code retains the variable as local to the inner block.
- Ruby utilizes the method
Proc#call
rather than a function call operator, which ECMAScript also employs (Function.prototype.call
).
- Ruby uses a custom iteration method on
Integer
, while your ECMAScript suggestion involves a for
loop.
- In Ruby,
Kernel#puts
writes implicitly to the default output stream, while your ECMAScript version explicitly writes to the console.
self
in Ruby is lexically bound, but in ECMAScript, this
is dynamically tied to the function object unless an arrow function literal is used, ensuring lexical binding of this
.
Conversely, the ECMAScript equivalent to:
(function (){
for (i = 0; i<10; i++){
console.log(i);
}
})()
Might be represented by:
-> { $i = 0; while $i < 10 do $stdout.puts($i); $i += 1 end }.()
Once again, this is not completely analogous:
- Ruby lacks a
for
loop and makes use of a while
loop instead.
- The call operator in Ruby is absent, with
.()
merely being syntactic sugar for the call
method.
this
in nested function expressions is dynamically bound, whereas self
remains lexically bound in Ruby.