Ruby - Array.Join Versus String Concatenation (Efficiency)

Ruby - Array.join versus String Concatenation (Efficiency)

Try it yourself with the Benchmark class.

require "benchmark"

n = 1000000
Benchmark.bmbm do |x|
x.report("concatenation") do
foo = ""
n.times do
foo << "foobar"
end
end

x.report("using lists") do
foo = []
n.times do
foo << "foobar"
end
string = foo.join
end
end

This produces the following output:

Rehearsal -------------------------------------------------
concatenation 0.300000 0.010000 0.310000 ( 0.317457)
using lists 0.380000 0.050000 0.430000 ( 0.442691)
---------------------------------------- total: 0.740000sec

user system total real
concatenation 0.260000 0.010000 0.270000 ( 0.309520)
using lists 0.310000 0.020000 0.330000 ( 0.363102)

So it looks like concatenation is a little faster in this case. Benchmark on your system for your use-case.

Ruby Array concat versus + speed?

According to the Ruby docs, the difference is:

Array#+ :

Concatenation — Returns a new array built by concatenating the two arrays together to produce a third array.

Array#concat :

Array#concat : Appends the elements of other_ary to self.

So the + operator will create a new array each time it is called (which is expensive), while concat only appends the new element.

Ruby differences between += and to concatenate a string

The shovel operator << performs much better than += when dealing with long strings because the shovel operator is allowed to modify the original string, whereas += has to copy all the text from the first string into a new string every time it runs.

There is no += operator defined on the String class, because += is a combined operator. In short x += "asdf" is exactly equivalent to x = x + "asdf", so you should reference the + operator on the string class, not look for a += operator.

How to efficiently concatenate multiple arrays in Ruby?

If you've already determined that multiple concatenation is the fastest method, you can write it nicer using reduce:

[foo, bar, baz].reduce([], :concat)

String concatenation in Ruby

You can do that in several ways:

  1. As you shown with << but that is not the usual way
  2. With string interpolation

    source = "#{ROOT_DIR}/#{project}/App.config"
  3. with +

    source = "#{ROOT_DIR}/" + project + "/App.config"

The second method seems to be more efficient in term of memory/speed from what I've seen (not measured though). All three methods will throw an uninitialized constant error when ROOT_DIR is nil.

When dealing with pathnames, you may want to use File.join to avoid messing up with pathname separator.

In the end, it is a matter of taste.

String concatenation vs. interpolation in Ruby

Whenever TIMTOWTDI (there is more than one way to do it), you should look for the pros and cons. Using "string interpolation" (the second) instead of "string concatenation" (the first):

Pros:

  • Is less typing
  • Automatically calls to_s for you
  • More idiomatic within the Ruby community
  • Faster to accomplish during runtime

Cons:

  • Automatically calls to_s for you (maybe you thought you had a string, and the to_s representation is not what you wanted, and hides the fact that it wasn't a string)
  • Requires you to use " to delimit your string instead of ' (perhaps you have a habit of using ', or you previously typed a string using that and only later needed to use string interpolation)

String Concatenation in Efficient Way

c = a + "," + b
# or
c = a << "," << b # warning: will modify 'a'

Just use simple string concatenation (the +/<< operator). Note that if you use <<, then a will be modified, so the first method is probably a better idea unless you don't care about a any more.


For many strings, first put them in an array:

myArray = ['some string', 'another string', 'string']

Then use the join function:

myArray.join(',') # some string,another string,string
# or
myArray * ',' # same as above, * is an alias for join

Ruby concatenate strings and add spaces

[name, quest, favorite_color, speed].reject(&:empty?).join(' ')


Related Topics



Leave a reply



Submit