【问题标题】:Regex to match first/last names with optional titles正则表达式将名字/姓氏与可选标题匹配
【发布时间】:2016-04-01 00:08:02
【问题描述】:

我创建了以下正则表达式(Java):

(Lord |Lady |Ser )?(Agatha|John)?([ ]??Cain)?

除了在一种情况下(可能还有我在测试期间没有考虑到的其他情况),它工作正常:

如您所见,当您只有姓氏时,正则表达式也会占用单词后面的空格。我完全明白为什么,但我不知道如何解决它。

此正则表达式用于在代表书籍内容的大文本文件中查找人员。当然,它必须与我当前的工作环境(Java)兼容。

【问题讨论】:

  • 为什么在 Cain 之前需要一个空格? (Lord |Lady |Ser )?(Agatha|John)?(Cain)?这样可以吗?
  • 不是真的,因为如果我有“Lord John Cain”,它将产生 2 个不同的匹配而不是一个。
  • 您确实意识到,如果在文本中某处写成My Lord (包括最后一个空格),您会遇到同样的问题,难道您不能直接在 Java 中修剪匹配项吗?
  • 我非常愿意这样做,但是我将它用于 NER 数据集。
  • 使用这样的可选组无法实现您想要的。它是固定模式还是动态构建?您可以尝试重新排列它,例如 \b(Lord|Lady|Ser)[ ](?:(Agatha|John)?(?:[ ](Cain))?)|(Agatha|John|Cain)\b

标签: java regex match


【解决方案1】:

您可以使用正则表达式回溯来实现您的目标。

\b(?<!\S)(?:(Lord|Lady|Ser)\s+)?(Agatha|John)?(?:\s*(?<=\b)(Cain))?(?<=\S)\b@ regex101

它具有似乎符合(可能超过)您的标准的这些品质:

  • 正则表达式匹配被强制以非空白字符开头。
  • 第一个捕获将是标题(或为空)。
  • 第二次捕获将是名字(或为空)。
  • 第三次捕获将是姓氏(或为空)。
  • 所有匹配项都没有前导或尾随空格。
  • 此外,它甚至可以通过换行进行匹配(显示在链接的正则表达式测试示例中的附加文本中)。
  • 头衔、名字和姓氏位于单个组中,因此添加到匹配集就像在各自的组中添加额外的替代一样简单。
  • 还添加了坚持以非空格结尾的匹配的尾随后视,以避免仅匹配其他不匹配的“Lord X”的“Lord”。

带有示例数据的 regex101 fiddle 链接到该正则表达式。

【讨论】:

  • 这正是我想要做的,但找不到方法。
  • 我的大部分正则表达式知识来自 Jeffrey E. F. Friedl 的“掌握正则表达式”;这是我的基准正则表达式参考。我还使用 (regular-expressions.info) 和 (rexegg.com) 作为在线参考,并使用 (regex101.com) 或 (regexr.com) 作为现场测试人员进行实验。
  • 太好了!非常感谢您的帮助!我唯一关心的是:有没有办法避免只匹配 Lord|Lady|Set 作为单个单词?例如,我正在匹配“Yes my lord!”。这与特定的人无关。
  • 奇数。这不应该匹配,因为(Lord|Lady|Ser)\s+ 必须有后面的空格,而且情况错误。此外,链接的 regex101 提琴手没有显示这样的匹配。但是,它确实与“Lord SomeOneElse”的“Lord”部分相匹配,这可能很麻烦。因此,我添加了一个尾随后视,它坚持比赛以非空格结尾,这也解决了这个问题。添加后,实时 regex101 不会显示与未知“Lord X”匹配的“Lord”。让我知道这是否可以为您解决问题。
猜你喜欢
  • 1970-01-01
  • 2016-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-09-13
  • 1970-01-01
相关资源
最近更新 更多