正则表达式替换所有不在引号中的令牌?

时间:2014-08-07 11:43:22

标签: javascript regex

我正在尝试用JavaScript处理一些输入数据,我需要替换所有字符串标记的出现(格式为" ID1"," ID2"," ID3",...)带有包装原始令牌的字符串。例如" ID1"成为"表[' ID1']"。但是,如果原始令牌包含在引号(单引号或双引号)中,则必须将其忽略。

例如输入字符串:

var input = "ID10 \"ID0\" FOO 'ID0' #ID0# ID10 BAR ID1 ID0.";

应该成为:

"table['ID10'] \"ID0\" FOO 'ID0' #table['ID0']# table['ID10'] BAR table['ID1'] table['ID0']."

我现在可以使用以下代码(Try it on jsbin.com here)获得一些方法:

var input = "ID10 \"ID0\" FOO 'ID0' #ID0# ID10 BAR ID1 ID0.";

var expected = "table['ID10'] \"ID0\" FOO 'ID0' #table['ID0']# table['ID10'] BAR table['ID1'] table['ID0'].";

// assume 15 is the max number of ids. we search backwards.
for( i=15 ; i>=0 ; i-- )
{
    var id = "ID" + i;

    var regex = new RegExp( "[^\"\']" + id + "", 'g' );

    input = input.replace( regex, "table['" + id + "']" );
}

if( input == expected )
    alert( 'success :)' );

这会产生输出:

ID10 "ID0" FOO 'ID0' table['ID0']#table['ID10'] BARtable['ID1']table['ID0'].

似乎接近工作,但第一个ID(ID10)被忽略,匹配前的第一个字符丢失。

任何人都可以建议如何正确处理,谢谢。

3 个答案:

答案 0 :(得分:1)

我认为你需要一个负面的前瞻标记。

看看here

整个正则表达式是

(ID\d+(?!\\))

否定前瞻是(?!...)。它只是断言数字后面的下一个字符不是反斜杠

所以代码将是

的代码
var re = /(ID\d+(?!\\))/g; 
var str = 'ID10 \"ID0\" FOO \'ID0\' #ID0# ID10 BAR ID1 ID0.';
var subst = 'table[\'$1\']'; 
var result = str.replace(re, subst);
// table['ID10'] \"ID0\" FOO 'table['ID0']' #table['ID0']# table['ID10'] BAR table['ID1'] table['ID0'].

答案 1 :(得分:1)

你可以使用这个正则表达式基于String#replace中的交替使用回调函数:

var input = "ID10 \"ID0\" FOO 'ID0' #ID0# ID10 BAR ID1 ID0.";
var r= input.replace(/"[^"]*"|'[^']*'|(ID\d+)/g, function($0, $1) {
       return ($1)? "table['"+$1+"']" : $0;});
//=> table['ID10'] "ID0" FOO 'ID0' #table['ID0']# table['ID10'] BAR table['ID1'] table['ID0'].

答案 2 :(得分:1)

编辑似乎Javascript中不支持零宽度负面后视,因此您需要零宽度负面预测来检查下一个字符ID加数字后不是反斜杠,单引号或双引号。

你可以尝试

/(ID\d+(?![\\\'\"]))/g

编辑忘掉这一切!

你需要一个零宽度负面观察

你可以尝试

/(?<![\"\'])ID\d+/g

或者,您可以尝试在群组中捕捉匹配

/[^\"\'](ID\d+)/g