title: Java multiple replace on a single pass
body: <p>I'm trying to translate nodes on a newick formatted tree, and I'm having trouble getting the replacing right. Say I have the <code>HashMap</code>:</p>
  
  <pre><code>"(1:" : "(30:"
  ",1:" : ",30:" 
  "(30:" : "(6:"
  ",30:" : ",6:"
  </code></pre>
  
  <p>And the tree:</p>
  
  <pre><code>(30:0.07,(1:0.06,2:0.76))
  </code></pre>
  
  <p>Conventional wisdom would suggest multiple <code>replaceAll</code>, but this poses a problem: </p>
  
  <pre><code>replaceAll("(1:", "(30:") &gt;&gt; (30:0.07,(30:0.06,2:0.76))
  replaceAll("(30:", "(6:") &gt;&gt; (6:0.07,(6:0.06,2:0.76))
  </code></pre>
  
  <p>The problem here is we've replaced a node that was previously replaced. The correct tree should look like:</p>
  
  <pre><code>(6:0.07,(30:0.06,2:0.76))
  </code></pre>
  
  <p>Now I've already done this in Python: </p>
  
  <pre><code>def multiple_replace(taxa, text): 
      regex = re.compile("|".join(map(re.escape, taxa.keys())))
      return regex.sub(lambda mo: taxa[mo.group(0)], text) 
  </code></pre>
  
  <p>But I'm having trouble with my Java implementation:</p>
  
  <pre><code>private String convertTree (String treeOld, HashMap&lt;String, String&gt; conv) {
          Pattern pattern = Pattern.compile("\\(\\d+:|,\\d+:");
          Matcher matcher = pattern.matcher(treeOld);
          StringBuilder sbt = new StringBuilder(treeOld);
          while (matcher.find()) {
              String replace = conv.get(matcher.group());
              System.out.println(matcher.group() + "||" +replace + " || " + matcher.start() + ":"+matcher.end());
              sbt.delete(matcher.start(), matcher.end());
              sbt.insert(matcher.start(), replace);
          }
          return treeOld;
  
      }
  </code></pre>
  
  <p>While the replacing appears to work, I can't get the indexing quite correct with different sizes of strings (as shown in the example). Is there a way to do this in Java?</p>