在字符串中查找查询匹配项
Find query matches within a string
我的任务是根据查询计算要在文本中突出显示的字符。
假设给定的文本是 "London, United Kingdom"
,查询是 "lond"
。那么结果应该是[[0, 4]]
.
我有一个简单的实现,适用于这种情况:
// ...
.reduce((result, word) => {
const wordLen = word.length;
const prefix = wordCharacterRegex.test(word[0]) ? "\b" : "";
const regex = new RegExp(prefix + escapeRegexCharacters(word), "i");
const index = text.search(regex);
if (index > -1) {
result.push([index, index + wordLen]);
text =
text.slice(0, index) +
new Array(wordLen + 1).join(" ") +
text.slice(index + wordLen);
}
return result;
}, [])
// ...
但是如果文本是 "EC2V 6DB, London, United Kingdom"
并且查询是 "ec2v6db"
它就不起作用,因为正则表达式将是 /\bec2v6db/i
。
那么,我该如何更改我的代码并解决问题呢?
首先,如果第一个字符是字符字符,则添加的单词边界应该与 non-word 个字符一致:如果在字符字符之前添加 \b
,请添加 \B
在 non-word 字符之前获得相同的行为。
const prefix = wordCharacterRegex.test(word[0]) ? "\b" : "\B";
然后,不清楚您的 escapeRegexCharacters
方法是什么样的,但您可以在关键字的每个字符之间插入 \s*
:
function escapeRegexCharacters(s) {
var res = s.replace(/([-\/\^$*+?.()|[\]{}])|[\s\S]/g, (m,g) => (g ? "\" + g : m) + "\s*");
return res.substring(0, res.length -3);
}
这是一个演示:
let word = "ec2v6db"; // lond is checked
let text = "EC2V 6DB, London, United Kingdom";
const wordCharacterRegex = /\w/;
function escapeRegexCharacters(s) {
var res = s.replace(/([-\/\^$*+?.()|[\]{}])|[\s\S]/g, (m,g) => (g ? "\" + g : m) + "\s*");
return res.substring(0, res.length -3);
}
const prefix = wordCharacterRegex.test(word[0]) ? "\b" : "\B";
const regex = new RegExp(prefix + escapeRegexCharacters(word), "i");
// Replacing text with spaces
console.log(text.replace(regex, m => " ".repeat(m.length)));
// => " , London, United Kingdom"
// Adding tags around the match
console.log(text.replace(regex, "<highlight>$&</highlight>"));
// Getting the indices:
let match = regex.exec(text);
if (match) {
console.log([match.index, match.index+match[0].length]);
}
我的任务是根据查询计算要在文本中突出显示的字符。
假设给定的文本是 "London, United Kingdom"
,查询是 "lond"
。那么结果应该是[[0, 4]]
.
我有一个简单的实现,适用于这种情况:
// ...
.reduce((result, word) => {
const wordLen = word.length;
const prefix = wordCharacterRegex.test(word[0]) ? "\b" : "";
const regex = new RegExp(prefix + escapeRegexCharacters(word), "i");
const index = text.search(regex);
if (index > -1) {
result.push([index, index + wordLen]);
text =
text.slice(0, index) +
new Array(wordLen + 1).join(" ") +
text.slice(index + wordLen);
}
return result;
}, [])
// ...
但是如果文本是 "EC2V 6DB, London, United Kingdom"
并且查询是 "ec2v6db"
它就不起作用,因为正则表达式将是 /\bec2v6db/i
。
那么,我该如何更改我的代码并解决问题呢?
首先,如果第一个字符是字符字符,则添加的单词边界应该与 non-word 个字符一致:如果在字符字符之前添加 \b
,请添加 \B
在 non-word 字符之前获得相同的行为。
const prefix = wordCharacterRegex.test(word[0]) ? "\b" : "\B";
然后,不清楚您的 escapeRegexCharacters
方法是什么样的,但您可以在关键字的每个字符之间插入 \s*
:
function escapeRegexCharacters(s) {
var res = s.replace(/([-\/\^$*+?.()|[\]{}])|[\s\S]/g, (m,g) => (g ? "\" + g : m) + "\s*");
return res.substring(0, res.length -3);
}
这是一个演示:
let word = "ec2v6db"; // lond is checked
let text = "EC2V 6DB, London, United Kingdom";
const wordCharacterRegex = /\w/;
function escapeRegexCharacters(s) {
var res = s.replace(/([-\/\^$*+?.()|[\]{}])|[\s\S]/g, (m,g) => (g ? "\" + g : m) + "\s*");
return res.substring(0, res.length -3);
}
const prefix = wordCharacterRegex.test(word[0]) ? "\b" : "\B";
const regex = new RegExp(prefix + escapeRegexCharacters(word), "i");
// Replacing text with spaces
console.log(text.replace(regex, m => " ".repeat(m.length)));
// => " , London, United Kingdom"
// Adding tags around the match
console.log(text.replace(regex, "<highlight>$&</highlight>"));
// Getting the indices:
let match = regex.exec(text);
if (match) {
console.log([match.index, match.index+match[0].length]);
}