问问题
1503 次
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 回答