字符串正则表达式反向引用

你可以像这样在 JavaScript 中反向引用:

var str = "123 $test 123";
str = str.replace(/(\$)([a-z]+)/gi, "$2");

这会(相当愚蠢)将“ $test”替换为“ test”。但是想象一下,我想将得到的 $2字符串传递给一个函数,该函数返回另一个值。我尝试这样做,但是得到的不是字符串“ test”,而是“ $2”。有办法做到吗?

// Instead of getting "$2" passed into somefunc, I want "test"
// (i.e. the result of the regex)
str = str.replace(/(\$)([a-z]+)/gi, somefunc("$2"));
53450 次浏览

Like this:

str.replace(regex, function(match, $1, $2, offset, original) { return someFunc($2); })

Pass a function as the second argument to replace:

str = str.replace(/(\$)([a-z]+)/gi, myReplace);


function myReplace(str, group1, group2) {
return "+" + group2 + "+";
}

This capability has been around since Javascript 1.3, according to mozilla.org.

Note: Previous answer was missing some code. It's now fixed + example.


I needed something a bit more flexible for a regex replace to decode the unicode in my incoming JSON data:

var text = "some string with an encoded 's' in it";


text.replace(/&#(\d+);/g, function() {
return String.fromCharCode(arguments[1]);
});


// "some string with an encoded 's' in it"

Using ESNext, quite a dummy links replacer but just to show-case how it works :

let text = 'Visit http://lovecats.com/new-posts/ and https://lovedogs.com/best-dogs NOW !';


text = text.replace(/(https?:\/\/[^ ]+)/g, (match, link) => {
// remove ending slash if there is one
link = link.replace(/\/?$/, '');
  

return `<a href="${link}" target="_blank">${link.substr(link.lastIndexOf('/') +1)}</a>`;
});


document.body.innerHTML = text;

If you would have a variable amount of backreferences then the argument count (and places) are also variable. The MDN Web Docs describe the follwing syntax for sepcifing a function as replacement argument:

function replacer(match[, p1[, p2[, p...]]], offset, string)

For instance, take these regular expressions:

var searches = [
'test([1-3]){1,3}',  // 1 backreference
'([Ss]ome) ([A-z]+) chars',  // 2 backreferences
'([Mm][a@]ny) ([Mm][0o]r[3e]) ([Ww][0o]rd[5s])'  // 3 backreferences
];
for (var i in searches) {
"Some string chars and many m0re w0rds in this test123".replace(
new RegExp(
searches[i]
function(...args) {
var match = args[0];
var backrefs = args.slice(1, args.length - 2);
// will be: ['Some', 'string'], ['many', 'm0re', 'w0rds'], ['123']
var offset = args[args.length - 2];
var string = args[args.length - 1];
}
)
);
}

You can't use 'arguments' variable here because it's of type Arguments and no of type Array so it doesn't have a slice() method.