<div dir="ltr"><div>My parallel string-compare sample provides two implementations (below).</div><div><br></div><div>Will both of these survive your changes?</div><div><br></div><div><a href="http://bitbucket.org/joebowbeer/stringcompare" target="_blank">bitbucket.org/joebowbeer/stringcompare</a><br>

</div><div><br></div><div><pre style="font-family:&#39;Bitstream Vera Sans Mono&#39;,&#39;DejaVu Sans Mono&#39;,Monaco,monospace;font-size:12px;line-height:1.4;margin-top:0px;margin-bottom:0px;color:rgb(51,51,51)">  <span style="color:rgb(68,85,136)">int</span> <span style="color:rgb(153,0,0)">compareMapReduce</span><span>(</span><span>String</span> <span>s1</span><span>,</span> <span>String</span> <span>s2</span><span>)</span> <span>{</span>
    <span style="color:rgb(0,64,128)">assert</span> <span>s1</span><span>.</span><span style="color:rgb(0,128,128)">length</span><span>()</span> <span>==</span> <span>s2</span><span>.</span><span style="color:rgb(0,128,128)">length</span><span>();</span>
    <span style="color:rgb(0,64,128)">return</span> <span style="color:rgb(153,0,0)">intRange</span><span>(</span><span style="color:rgb(0,153,153)">0</span><span>,</span> <span>s1</span><span>.</span><span style="color:rgb(0,128,128)">length</span><span>()).</span><span style="color:rgb(0,128,128)">parallel</span><span>()</span>
        <span>.</span><span style="color:rgb(0,128,128)">map</span><span>(</span><span>i</span> <span>-&gt;</span> <span>compare</span><span>(</span><span>s1</span><span>.</span><span style="color:rgb(0,128,128)">charAt</span><span>(</span><span>i</span><span>),</span> <span>s2</span><span>.</span><span style="color:rgb(0,128,128)">charAt</span><span>(</span><span>i</span><span>)))</span>
        <span>.</span><span style="color:rgb(0,128,128)">reduce</span><span>(</span><span style="color:rgb(0,153,153)">0</span><span>,</span> <span>(</span><span>l</span><span>,</span> <span>r</span><span>)</span> <span>-&gt;</span> <span>(</span><span>l</span> <span>!=</span> <span style="color:rgb(0,153,153)">0</span><span>)</span> <span>?</span> <span>l</span> <span>:</span> <span>r</span><span>);</span>
  <span>}</span>
<a name="13cca2bd7f4b0f7c_cl-18" style="color:rgb(60,119,180)"></a>
  <span style="color:rgb(68,85,136)">int</span> <span style="color:rgb(153,0,0)">compareBoxedReduce</span><span>(</span><span>String</span> <span>s1</span><span>,</span> <span>String</span> <span>s2</span><span>)</span> <span>{</span>
    <span style="color:rgb(0,64,128)">assert</span> <span>s1</span><span>.</span><span style="color:rgb(0,128,128)">length</span><span>()</span> <span>==</span> <span>s2</span><span>.</span><span style="color:rgb(0,128,128)">length</span><span>();</span>
    <span style="color:rgb(0,64,128)">return</span> <span style="color:rgb(153,0,0)">intRange</span><span>(</span><span style="color:rgb(0,153,153)">0</span><span>,</span> <span>s1</span><span>.</span><span style="color:rgb(0,128,128)">length</span><span>()).</span><span style="color:rgb(0,128,128)">parallel</span><span>().</span><span style="color:rgb(0,128,128)">boxed</span><span>()</span>
        <span>.</span><span style="color:rgb(0,128,128)">reduce</span><span>(</span><span style="color:rgb(0,153,153)">0</span><span>,</span> <span>(</span><span>l</span><span>,</span> <span>i</span><span>)</span> <span>-&gt;</span> <span>(</span><span>l</span> <span>!=</span> <span style="color:rgb(0,153,153)">0</span><span>)</span> <span>?</span> <span>l</span> <span>:</span> <span>compare</span><span>(</span><span>s1</span><span>.</span><span style="color:rgb(0,128,128)">charAt</span><span>(</span><span>i</span><span>),</span> <span>s2</span><span>.</span><span style="color:rgb(0,128,128)">charAt</span><span>(</span><span>i</span><span>)),</span>
                   <span>(</span><span>l</span><span>,</span> <span>r</span><span>)</span> <span>-&gt;</span> <span>(</span><span>l</span> <span>!=</span> <span style="color:rgb(0,153,153)">0</span><span>)</span> <span>?</span> <span>l</span> <span>:</span> <span>r</span><span>);</span>
  <span>}</span></pre><pre style="font-family:&#39;Bitstream Vera Sans Mono&#39;,&#39;DejaVu Sans Mono&#39;,Monaco,monospace;font-size:12px;line-height:1.4;margin-top:0px;margin-bottom:0px;color:rgb(51,51,51)"><span><br>
<br></span></pre>The person who sold me the second form told me it would &quot;burn less heat&quot;. He said that I could optimize my map/reduce by having it &quot;not even calculate <b>f</b> if the left operand is nonzero, by combining the map and reduce steps into a fold.&quot;</div>
<div><br></div><div style>What is that person going to sell me now?</div><div style><br></div><div style>Joe</div></div><div class="gmail_extra"><br><br><div class="gmail_quote">On Mon, Feb 11, 2013 at 8:41 AM, Brian Goetz <span dir="ltr">&lt;<a href="mailto:brian.goetz@oracle.com" target="_blank">brian.goetz@oracle.com</a>&gt;</span> wrote:<br>
<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Now that we&#39;ve added all the shapes of map() to Stream (map to ref/int/long/double), and we&#39;ve separated functional reduce (currently called reduce) from mutable reduce (currently called collect), I think that leaves room for taking out one of the reduce methods from Stream:<br>

<br>
    &lt;U&gt; U reduce(U identity,<br>
                 BiFunction&lt;U, ? super T, U&gt; accumulator,<br>
                 BinaryOperator&lt;U&gt; reducer);<br>
<br>
This is the one that confuses everyone anyway, and I don&#39;t think we need it any more.<br>
<br>
The argument for having this form instead of discrete map+reduce are:<br>
 - fused map+reduce reduces boxing<br>
 - this three-arg form can also fold filtering into the accumulation<br>
<br>
However, since we now have primitive-bearing map methods, and we can do filtering before and after the map, is this form really carrying its weight?  Specifically because people find it counterintuitive, we should consider dropping it and guiding people towards map+reduce.<br>

<br>
For example, &quot;sum of pages&quot; over a stream of Documents is better written as:<br>
<br>
  docs.map(Document::<u></u>getPageCount).sum()<br>
<br>
rather than<br>
<br>
  docs.reduce(0, (count, d) -&gt; count + d.getPageCount(), Integer::sum)<br>
<br>
The big place where we need three-arg reduce is when we&#39;re folding into a mutable store.  But that&#39;s now handled by collect().<br>
<br>
Have I missed any use cases that would justify keeping this form?<br>
<br>
</blockquote></div><br></div>