“匹配嵌套的括号需要用到正则表达式中的平衡组语法,但遗憾的是javascript中不支持平衡组语法,所以单用一条正则表达式实现不了,需要用循环逐个字符处理。”
场景demo:
var str_ = "{aaa} is {"{}{}}}}\{}" == {ccc}}";
需求:提取分割所有 {}节点
分割得到结果:
第1组 "{aaa}"
第2组 " is "
第3组 "{"{}{}}}}{}" == {ccc}}"
var splitStrByKh = function(s) {
if(!/{{([^\}]+)}}/.test(s) && !/{([^\}]+)}/.test(s)) return s;
var getOutStr = function(s) {
var tmpSplitTag = 'lrSplit';
var N =0;
var newStr = s;
newStr = newStr.replace(/({|})/g, function($0,$1)
{
if($1==="{") {
return "<"+tmpSplitTag+(++N)+">";
}
if($1==="}"){
return "</"+ tmpSplitTag+ (N--) +">";
}
});
//将首节点复原成 { }
var regAdd1_ = new RegExp("<"+tmpSplitTag+"1>", 'g');
newStr = newStr.replace(regAdd1_, '{');
var regAdd2_ = new RegExp("<\/"+tmpSplitTag+"1>", 'g');
newStr = newStr.replace(regAdd2_, '}');
//提取首级节点
var reg_ = new RegExp("{([^\}]+)}");
var firstTagArray = [];
function findFirstTagStr(restStr) {
var findTag = restStr.match(reg_);
if(findTag) {
var findIndex = findTag.index;
if(findIndex===0) {
firstTagArray.push(findTag[0]);
} else {
firstTagArray.push(restStr.slice(0, findIndex));
firstTagArray.push(findTag[0]);
}
var rightStr = restStr.slice(findIndex + (findTag[0].length));
if(rightStr) {
findFirstTagStr(rightStr);
}
} else {
firstTagArray.push(restStr);
}
}
findFirstTagStr(newStr);
//复原
var removeReg1 = new RegExp("<"+tmpSplitTag+"\\d+>", 'g');
var removeReg2 = new RegExp("<\/"+tmpSplitTag+"\\d+>", 'g');
firstTagArray.map(function (str_, n) {
var newStr = str_;
newStr = newStr.replace(removeReg1, '{');
newStr = newStr.replace(removeReg2, '}');
if(newStr !== str_) {
firstTagArray[n] = newStr;
}
});
return firstTagArray;
};
var result = getOutStr(s);
$.each(result, function (n, v) {
result[n] = v;
});
return result;
};