【问题标题】:Searching for any articles where one column matches any of multiple regular expressions搜索其中一列与多个正则表达式中的任何一个匹配的任何文章
【发布时间】:2021-02-25 16:01:24
【问题描述】:

我有一个非常具体的挑战,经过我所有的搜索,我似乎无法找到答案。我正在寻找 MongoDB 中的一篇文章,其中“内容”列与多个可能的正则表达式中的任何一个匹配。

一般的想法是,我想输入一个单词,然后返回与该单词匹配的任何列以及带有任何后缀的单词。例如:

如果用户输入“建立”,我想搜索内容列包含以下任何一项的文章:“建立”、“建立”、“建立”、“建立”等...

我可以生成可能的字符串列表来搜索自己,但是如何在 MongoDB 中使用 .find 来搜索我的文章?

我的代码目前看起来像这样,它可以很好地搜索一个字符串,我只需要搜索 MULTIPLE:

// get all articles with phrase = ?
router.get('/articlesByPhrase', async (req, res) => {
  const { person_id, phrase } = req.query;

  try {
    const articles = await Article.find({
      person_id,
      content: { $regex: phrase, $options: 'i' },
    })
    res.json(articles)
  } catch (err) {
    res.status(500).json({ message: err.message })
  }
})

我想我需要使用我所有可能的字符串生成一个 RegExp,但我不太确定如何实现它。任何帮助表示赞赏!

【问题讨论】:

  • 知道establish可以成功的所有案例吗?或者在单词结束之前允许任何事情?
  • 有很多不同的解决方案。只要一个人不准确地知道用例及其条件/规范,那么简单的事情就可以了。 /^establish/.startsWith('establish') 的正则表达式)可能已经足够了。那么,字符串可能看起来像那个 "... 只需要搜索 MULTIPLE"

标签: javascript node.js mongodb


【解决方案1】:

如果单词的词根不会改变,并且您确切地知道要查找的后缀,那么离开您给出的示例,您可以像这样使用正则表达式:

"establish(?:ment|es|ed)?\b"

在上面的字符串中,表达式(?:<blah>)被称为非捕获组。它用于匹配一组字符(无需重新引用它们,例如在进行替换时)。在该组内,您可以指定要匹配的多个选项,并使用分隔符| 将它们拆分。

末尾的? 指定要匹配前面元素的0 或1。最后,\b 匹配一个单词分隔符(空格、标点符号等)

请记住,您形成的任何正则表达式字符串都必须提供给 Regexpr 构造函数,因此您需要注意正确转义字符(这里是 reference)。这给出了:

var regex_string = 'establish\(\?:ment\|es\|ed\)\?\\b'

Javascript 可以通过使用String.raw 轻松解决此问题:

const regexString = String.raw`establish(?:ment|es|ed)?\b`

【讨论】:

  • 不……你自己试过了吗?您正在使用character class,但它已经很接近了。
  • 还是不行......因为正则表达式模式被写成字符串,因此需要提供给RegExp 构造函数,它需要更多的转义。你还是没有尝试。
  • ...哦,伙计...您在发布代码之前是否真的尝试过自己...var regex_string = String.raw('establish(?:ment|es|ed)?\b')...立即失败...必须是const regexString = String.raw`establish(?:ment|es|ed)?\b`
  • 原谅我,我从来没有使用过 Javascript,所以试图脱离参考。感谢您的耐心和乐于助人!
  • 谢谢!这对你们俩都非常有帮助。我会发布我最终做的事情。
【解决方案2】:

感谢大家的帮助。我基本上使用了 Ali Dowair 的答案。但这是我最终得到的结果:

// get all articles with phrase = ?
router.get('/articlesByPhrase', async (req, res) => {
  const { person_id, phrase, all_forms } = req.query;
  var regExp;
  if (all_forms === 'true') {
    const { suffixes } = forms;
    const suffixInserts = suffixes.join('|');
    regExp = String.raw`${phrase}(?:${suffixInserts})?\b`
  } else {
    regExp = String.raw`${phrase}\b`
  }
  try {
    console.log(`searching with :${regExp}`)
    const articles = await Article.find({
      person_id,
      content: { $regex: regExp, $options: 'gi' },
    })
    res.json(articles)
  } catch (err) {
    res.status(500).json({ message: err.message })
  }
})

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-08-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-05-12
    相关资源
    最近更新 更多