3
4

3 回答 3

3

Without DOM parsing you are going to have edge cases which will fail. But, this should work for you.

Given this HTML:

Hello :) <pre>Wassup :)</pre> Maybe :) <code>:) Foo</code> :) Bar

Use this code:

var blocks = [];
html = html.replace(/(?:<pre>.*?<\/pre>|<code>.*?<\/code>)/g, function (match) {
    blocks.push( match );
    return '__BLOCK__';
});

html = html.replace(/:\)/g, 'SMILE');

html = html.replace(/__BLOCK__/g, function () {
    return blocks.shift();
});

Which produces:

Hello SMILE <pre>Wassup :)</pre> Maybe SMILE <code>:) Foo</code> SMILE Bar

Just adjust the /:\)/g replace to work however you need it.

于 2014-01-27T03:08:12.577 回答
3

Guess you're using nodejs or a recent javascript engine (for "map" & "split" implementations), so you can do this:

function replaceSpecial(str, pattern, replacement) {
  var REG = /(<code>.*?<\/code>)|(<pre>.*?<\/pre>)/i;
  return str.split(REG).map(function(s) {
    if ('' + s !== s)
      return '';
    if (s.match(REG))
      return s;
    return s.replace(pattern, replacement);
  }).join('');
}

Example:

replaceSpecial("hey :) <code>:)</code> :'( <pre> :'( :)</pre>", /(:\))|(:'\()/, function(s) {
  switch(s) {
    case ":)":
      return '<img src="smile.gif" />';
    case ":'(":
      return '<img src="cry.gif" />';
  }
})

Will return:

"hey <img src="smile.gif" /> <code>:)</code> <img src="cry.gif" /> <pre> :'( :)</pre>"

Or easier if you just want to replace an emoticon:

replaceSpecial("hey :) <code>:)</code>", ":)", '<img src="smile.gif" />')

=>

"hey <img src="smile.gif" /> <code>:)</code>"
于 2014-01-27T03:57:53.990 回答
2
var co = -1, ce = 0, start=0, result; 
while ( ce != -1 ) {
   co = testString.indexOf('<code', ce);
   if (co > -1) {
     result += parse(testString.substring(start,co), pattern1); 
     start = co+1;
     ce = testString.indexOf('</code>', co + 5);
     if (ce >-1 ){
        start = ce + 7;
        ce = start;
        result += testString.substring(co,ce);
     }
  }
}
result += parse(testString.substring(start), pattern1);

console.log(result);

于 2014-01-27T04:09:45.807 回答