gpt4 book ai didi

Javascript Lookbehind 与全局搜索重叠

转载 作者:行者123 更新时间:2023-11-29 15:33:59 26 4
gpt4 key购买 nike

Javascript 中的 lookbehind regexps 有几种(有时是棘手的)解决方案。但是,这是最简单的方法,如果我需要一个零宽度! 使用全局搜索查看表达式,这可能会重叠。例如。使用 /(?<=[01])\d/g我们可以做以下事情:

let a = "--1--01001--1087---";
let result = a.replace(/(?<=[01])\d/g, "#");
// This should print "--1--0####--1##7---" if lookbehind would be supported
console.log(result);

或者另一个例子:我们如何创建一个 \b like 仅适用于字母的表达式 ( [a-zA-Z] )。 (lookforward没问题,只是JS不支持lookbehind)。

最佳答案

通过反转进行回顾 方法在这里似乎是最简单的。这种方法最适合像这样的短数字模式。

function revStr(str) {
return str.split('').reverse().join('');
}

var s = "--1--01001--1087---";
var rxp = /\d(?=[01])/g;

var result = revStr(revStr(s).replace(rxp, "#"));
document.write(result);

逻辑:

  • \d(?=[01])(?<=[01])\d 的反向正则表达式
  • 我们用 revStr(s) 反转输入字符串功能
  • 我们再次反转替换结果以获得最终结果。

注意:

如果您在 JavaScript 中同时需要可变宽度的后视 前视,我建议您阅读 JavaScript Regex Lookbehind Redux Steven Levithan 的文章,您可以在其中找到展示如何使用 XRegExp 实现该行为的示例函数.以下是函数:

// Simulating infinite-length leading lookbehind in JavaScript. Uses XRegExp.
// Captures within lookbehind are not included in match results. Lazy
// repetition in lookbehind may lead to unexpected results.

(function (XRegExp) {

function prepareLb(lb) {
// Allow mode modifier before lookbehind
var parts = /^((?:\(\?[\w$]+\))?)\(\?<([=!])([\s\S]*)\)$/.exec(lb);
return {
// $(?!\s) allows use of (?m) in lookbehind
lb: XRegExp(parts ? parts[1] + "(?:" + parts[3] + ")$(?!\\s)" : lb),
// Positive or negative lookbehind. Use positive if no lookbehind group
type: parts ? parts[2] === "=" : !parts
};
}

XRegExp.execLb = function (str, lb, regex) {
var pos = 0, match, leftContext;
lb = prepareLb(lb);
while (match = XRegExp.exec(str, regex, pos)) {
leftContext = str.slice(0, match.index);
if (lb.type === lb.lb.test(leftContext)) {
return match;
}
pos = match.index + 1;
}
return null;
};

XRegExp.testLb = function (str, lb, regex) {
return !!XRegExp.execLb(str, lb, regex);
};

XRegExp.searchLb = function (str, lb, regex) {
var match = XRegExp.execLb(str, lb, regex);
return match ? match.index : -1;
};

XRegExp.matchAllLb = function (str, lb, regex) {
var matches = [], pos = 0, match, leftContext;
lb = prepareLb(lb);
while (match = XRegExp.exec(str, regex, pos)) {
leftContext = str.slice(0, match.index);
if (lb.type === lb.lb.test(leftContext)) {
matches.push(match[0]);
pos = match.index + (match[0].length || 1);
} else {
pos = match.index + 1;
}
}
return matches;
};

XRegExp.replaceLb = function (str, lb, regex, replacement) {
var output = "", pos = 0, lastEnd = 0, match, leftContext;
lb = prepareLb(lb);
while (match = XRegExp.exec(str, regex, pos)) {
leftContext = str.slice(0, match.index);
if (lb.type === lb.lb.test(leftContext)) {
// Doesn't work correctly if lookahead in regex looks outside of the match
output += str.slice(lastEnd, match.index) + XRegExp.replace(match[0], regex, replacement);
lastEnd = match.index + match[0].length;
if (!regex.global) {
break;
}
pos = match.index + (match[0].length || 1);
} else {
pos = match.index + 1;
}
}
return output + str.slice(lastEnd);
};

}(XRegExp));

这些函数中的每一个都有三个参数:要搜索的字符串、作为字符串的后视模式(可以使用 XRegExp 语法扩展)和主正则表达式。 XRegExp.replaceLb接受第四个参数作为替换值,可以是字符串或函数。

用法示例如下:

XRegExp.execLb("Fluffy cat", "(?i)(?<=fluffy\\W+)", XRegExp("(?i)(?<first>c)at"));
// -> ["cat", "c"]
// Result has named backref: result.first -> "c"

XRegExp.execLb("Fluffy cat", "(?i)(?<!fluffy\\W+)", /cat/i);
// -> null

XRegExp.testLb("Fluffy cat", "(?i)(?<=fluffy\\W+)", /cat/i);
// -> true

XRegExp.testLb("Fluffy cat", "(?i)(?<!fluffy\\W+)", /cat/i);
// -> false

XRegExp.searchLb("Catwoman's fluffy cat", "(?i)(?<=fluffy\\W+)", /cat/i);
// -> 18

XRegExp.searchLb("Catwoman's fluffy cat", "(?i)(?<!fluffy\\W+)", /cat/i);
// -> 0

XRegExp.matchAllLb("Catwoman's cats are fluffy cats", "(?i)(?<=fluffy\\W+)", /cat\w*/i);
// -> ["cats"]

XRegExp.matchAllLb("Catwoman's cats are fluffy cats", "(?i)(?<!fluffy\\W+)", /cat\w*/i);
// -> ["Catwoman", "cats"]

XRegExp.replaceLb("Catwoman's fluffy cat is a cat", "(?i)(?<=fluffy\\W+)", /cat/ig, "dog");
// -> "Catwoman's fluffy dog is a cat"

XRegExp.replaceLb("Catwoman's fluffy cat is a cat", "(?i)(?<!fluffy\\W+)", /cat/ig, "dog");
// -> "dogwoman's fluffy cat is a dog"

XRegExp.replaceLb("Catwoman's fluffy cat is a cat", "(?i)(?<!fluffy\\W+)", /cat/ig, function ($0) {
var first = $0.charAt(0);
return first === first.toUpperCase() ? "Dog" : "dog";
});
// -> "Dogwoman's fluffy cat is a dog"

关于Javascript Lookbehind 与全局搜索重叠,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31570425/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com