535 views
What is the return value of the following Ruby code?
["a", *["b", "c"], "d"] * ?: # => ???
The correct answer is
["a:", "b:", "c:", "d:"]
"a:b:c:d"
["a:", ["b", "c"], "d:"]
It raises SyntaxError
Subscribe to RubyCademy and get free access to all our courses, plus hundreds of fun Ruby cards, quizzes, guides, and tutorials!
Let's detail step-by-step what occurs in the following line of code
["a", *["b", "c"], "d"] * ?: # => "a:b:c:d"
*["b", "c"]
concatenates the sub-array elements into the main array.
So after this operation, the array looks like this:
a = ["a", *["b", "c"], "d"] a # => ["a", "b", "c", "d"]
This idiom is particularly used in CSV generation when the number of columns can only be known at runtime.
book = Book.preload(:authors).find(123) row = [book.title, book.short_description, *book.authors.pluck(:fullname)] row # => ["Hello", "A book about Hello", "Author 1", "Author 2", "Author 3"]
?:
is a shorthand to create a single character string.
So
["a", "b", "c", "d"] * ?:
is equivalent to
["a", "b", "c", "d"] * ':'
When Array#*
takes a string as an argument, it acts like Array#join(sep)
.
Here
["a", "b", "c", "d"] * ':'
is equivalent to
["a", "b", "c", "d"].join(':')
So the return value of ["a", "b", "c", "d"] * ?:
is "a:b:c:d"
.
Voilà!
Subscribe to RubyCademy and get free access to all our courses, plus hundreds of fun Ruby cards, quizzes, guides, and tutorials!
RubyCademy ©