Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    text
    copied!<p>Let's try an example.</p> <pre><code>numbers = [ 3, 1, 4, 1, 5, 9 ] sum = numbers.inject(0) do |prefix_sum, number| prefix_sum + number end </code></pre> <p><code>#inject</code> takes one argument and a block. The block should take two values, and return a new value.</p> <p>In the above example, the argument to <code>#inject</code> is <code>0</code>, and the block is <code>do |prefix_sum, number| prefix_sum + number end</code>. The values that will be passed to the block are named in between the two <code>|</code> markers: <code>prefix_sum</code> and <code>number</code>.</p> <p>Each value of the enumerable <code>#inject</code> was called on is passed as the second value to the block in turn. In this example <code>number</code> will be <code>3</code>, then <code>1</code>, then <code>4</code>, then <code>1</code>, then <code>5</code>, then finally <code>9</code>. So in this example, the block will be invoked six times; once for each position in <code>numbers</code>.</p> <p>The first value passed to a block (here named <code>prefix_sum</code>) is usually called an <em>accumulator</em>. Its initial value, the value used the first time the block is called by <code>#inject</code>, is set by the argument passed to <code>#inject</code> (in this example, <code>0</code>). The return value of the block determines the value of the accumulator (<code>prefix_sum</code>) for the next invocation of the block.</p> <p>When there are no more elements to process, the value of the accumulator is returned (and here stored in <code>sum</code>).</p> <p>So lets walk through it:</p> <ul> <li><code>#inject</code> receives <code>0</code> and our block.</li> <li><code>#inject</code> invokes our block, binding <code>prefix_sum</code> to <code>0</code> (the initial accumulator value) and <code>number</code> to <code>3</code> (the first array value).</li> <li>our block calculates <code>0+3</code> as <code>3</code> and returns it.</li> <li><code>#inject</code> invokes our block, binding <code>prefix_sum</code> to <code>3</code> (the returned value) and <code>number</code> to <code>1</code> (the second array value)</li> <li>our block calculates <code>3+1</code> as <code>4</code> and returns it.</li> <li><code>#inject</code> invokes our block, binding <code>prefix_sum</code> to <code>4</code> (the returned value) and <code>number</code> to <code>4</code> (the third array value)</li> <li>our block calculates <code>4+4</code> as <code>8</code> and returns it.</li> <li><code>#inject</code> invokes our block, binding <code>prefix_sum</code> to <code>8</code> (the returned value) and <code>number</code> to <code>1</code> (the fourth array value)</li> <li>our block calculates <code>8+1</code> as <code>9</code> and returns it.</li> <li><code>#inject</code> invokes our block, binding <code>prefix_sum</code> to <code>9</code> (the returned value) and <code>number</code> to <code>5</code> (the fifth array value)</li> <li>our block calculates <code>9+5</code> as <code>14</code> and returns it.</li> <li><code>#inject</code> invokes our block, binding <code>prefix_sum</code> to <code>14</code> (the returned value) and <code>number</code> to <code>9</code> (the sixth array value)</li> <li>our block calculates <code>14+9</code> as <code>23</code> and returns it.</li> <li>since there are no more array elements, <code>#inject</code> returns <code>23</code>, and we bind <code>sum</code> to be that value.</li> </ul> <p>You can look at inject as parenthesizing an operation on a list of items, in this example, caluculating:</p> <pre><code>((((((0 + 3) + 1) + 4) + 1) + 5) + 9) </code></pre> <p>This lets you take any operation which normally only operates on a pair of arguments, and apply it to a list.</p>
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload