在使用OR
(管道)的正则表达式中,有一种方便的方法来获取匹配的表达式部分。
示例:
/horse|caMel|TORTOISe/i.exec("Camel");
返回Camel
。我想要的是caMel
。
我知道我可以遍历选项而不是使用一个大的正则表达式;这会更有意义。但我很想知道是否可以这样做。
答案 0 :(得分:5)
很简单,没有。
正则表达式匹配与您的输入字符串有关,而不是用于创建正则表达式的文本。请注意,该文本可能会丢失,理论上甚至不需要。一个等效的匹配器可以用这样的东西构建:
var test = function(str) {
var text = str.toLowerCase();
return text === "horse" || text === "camel" || text === "tortoise";
};
另一种思考方式是正则表达式的编译可以将函数的逻辑与其文本表示分开。它是单向的。
对不起。
答案 1 :(得分:3)
Javascript RegExp对象没有内置的方法;没有改变你的表达。你可以得到的最接近的是source
,它只会将整个表达式作为字符串返回。
由于您知道您的表达式是一系列| OR
,因此您可以捕获组以确定哪个组匹配,并将其与.source
组合以查找该组的内容:
var exp = /(horse)|(caMel)|(TORTOISe)/i;
var result = exp.exec("Camel");
var match = function(){
for(var i = 1; i < result.length; i++){
if(result[i]){
return exp.source.match(new RegExp('(?:[^(]*\\((?!\\?\\:)){' + i + '}([^)]*)'))[1];
}
}
}();
// match == caMel
从头开始编写RegExp引擎也非常容易(尽管有些不切实际),您可以在技术上添加该功能。它比使用实际的RegExp对象要慢得多,因为必须在运行时解释整个引擎。但是,它可以准确地返回任何正则表达式的表达式的匹配部分,而不限于由一系列| OR
s组成的表达式。
然而,解决问题的最佳方法可能根本不是使用循环或正则表达式,而是创建一个对象使用规范形式的对象:
var matches = {
'horse': 'horse',
'camel': 'caMel',
'tortoise': 'TORTOISe'
};
// Test "Camel"
matches['Camel'.toLowerCase()]; // "caMel"
答案 2 :(得分:2)
这将给出想要的值而不循环:
var foo, pat, tres, res, reg = /horse|caMel|TORTOISe/i;
foo = reg.exec('Camel');
if (foo) {
foo = foo[0].replace(/\./g, '\\.');
pat = new RegExp('\\|' + foo + '\\|', 'i');
tres = '|' + reg.source + '|';
res = tres.match(pat)[0].replace(/\|/g, '');
}
alert(res);
如果没有匹配,现在你得到undefined
,虽然很容易改成其他东西。