将返回组匹配项的 Javascript RegEx.exec 转换为 Python

Convert Javascript RegEx.exec which returns group matches to Python

提问人:KyferEz 提问时间:3/23/2019 最后编辑:Mikhail VladimirovKyferEz 更新时间:3/23/2019 访问量:1036

问:

我在 Javascript 中有这个代表性代码:

    NameRegEx = /\w+ \w+ (".*?"|\S+) (".*?"|\S+)/;
    term = NameRegEx.exec("add cmd item configname AAA 10.0.0.1 80 -option NONE -option2 YES -Option3 180");

这有效,“term”是一个包含以下内容的数组:

0: "add cmd item configname"
1: "item"
2: "configname"

我无法在 Python 中找到与 exec 函数等效的函数,希望得到一些帮助!我还需要转换许多类似的正则表达式命令,所以我需要一个接近的 Python 替代方案。

编辑: 这与链接的重复项不同,因为它们没有解决返回的值如何不同的事实。但是,Pushpesh Kumar Rajwanshi 通过对正则表达式的以下修改和以下解释解决了这个问题:

s = 'add cmd item configname AAA 10.0.0.1 80 -option NONE -option2 YES -Option3 180'
arr = [s for s in re.findall(r'(\w+ \w+ (".*?"|\S+) (".*?"|\S+))',s)[0]]
print(arr)

是的,需要额外的括号,因为您希望在数组结果中也捕获完整的字符串。否则,findall 仅包含组的结果,如果没有组,则整个匹配。

重新打开,因为作为重复链接的问题不能完全解决问题。

JavaScript 则表达 python-3.x

评论

1赞 Pushpesh Kumar Rajwanshi 3/23/2019
试试这个 Python 代码 它打印这个数组import re s = 'add cmd item configname AAA 10.0.0.1 80 -option NONE -option2 YES -Option3 180' arr = [s for s in re.findall(r'(\w+ \w+ (".*?"|\S+) (".*?"|\S+))',s)[0]] print(arr)['add cmd item configname', 'item', 'configname']
1赞 KyferEz 3/23/2019
@PushpeshKumarRajwanshi谢谢!请添加此作为答案,我会接受的。在正则表达式中添加括号就成功了!
1赞 Pushpesh Kumar Rajwanshi 3/23/2019
@KyferEz:是的,需要额外的括号,因为您希望在数组结果中也捕获完整的字符串。否则,仅包括仅组的结果,如果没有组,则整个匹配。这篇文章已经被标记为重复,所以不能添加为答案,但我很高兴我能帮你:)findall
1赞 Pushpesh Kumar Rajwanshi 3/23/2019
@WiktorStribiżew:在 Javascript 中,返回一个匹配数组,其中包含完全匹配项和随后分组的匹配项。OP 想要一个类似的函数,当使用时可以将结果作为数组返回,就像 Python 返回一个匹配对象一样,并且必须使用 match 对象手动构造数组。其中 as 可以相对更容易地做到这一点,因此更接近 JS 中的函数。execexecre.searchre.findallexec
1赞 Pushpesh Kumar Rajwanshi 3/23/2019
@WiktorStribiżew:如果您看到上面的帖子,OP 确实只想获得单个(第一个)匹配,这就是为什么我也在上面评论中发布的代码中使用了结果的第 0 个元素。我知道可以在循环中迭代以找到所有可能的匹配结果,但 OP 似乎只对第一场比赛感兴趣。这也是为什么我在第一条评论中写道,findall 即使不完全相同,也会做类似的工作。[0]findallexec

答:

1赞 Pushpesh Kumar Rajwanshi 3/23/2019 #1

首先,感谢大家都同意应该重新打开这篇文章,因为链接的帖子对 OP 正在寻找的东西没有帮助。

在回答时,我的主要目的是使解决方案接近 JS 中的函数调用(而不是性能,这当然会更好,而不是因为后者做了比需要更多的工作,但只使用数组中的第一个元素),并且作为 JS 中的函数返回一个结果数组,Python 中的类似函数返回结果,例如数组是。execsearchfindallexecfindall

就像 JS 中 OP 的正则表达式没有全局标志 ON 一样,这意味着他只对第一场比赛感兴趣,我使用了结果的第一个元素,我的 Python 代码解决方案是这样的,/\w+ \w+ (".*?"|\S+) (".*?"|\S+)/[0]findall

import re
s = 'add cmd item configname AAA 10.0.0.1 80 -option NONE -option2 YES -Option3 180'
arr = [s for s in re.findall(r'(\w+ \w+ (".*?"|\S+) (".*?"|\S+))', s)[0]]
print(arr)

其中打印,

['add cmd item configname', 'item', 'configname']

但是函数也可以实现同样的目的,因为它逐个迭代搜索,因此它比通过在一次操作中扫描整个字符串来找到所有可能的结果要好,这与仅通过访问数组中的第一个元素来首先使用不同。因此,使用与该功能过于相似的功能发布解决方案也可以被 OP 使用并且性能会更好,因为这只会寻找第一个匹配项。由于返回一个元组,但 OP 想要一个数组,因此需要此代码,因此 OP 可以完全按照 JS 中的方法返回的方式获得数组中的结果。searchfindallfindallsearchsearchfindallgroups()exec

import re
s = 'add cmd item configname AAA 10.0.0.1 80 -option NONE -option2 YES -Option3 180'
m = re.search(r'(\w+ \w+ (".*?"|\S+) (".*?"|\S+))', s)
if (m):
 arr = [s for s in m.groups()]
 print(arr)

指纹

['add cmd item configname', 'item', 'configname']

但是,是的,JS的正则表达式需要进行一次更改,将整个正则表达式括在一个额外的括号中,否则它就不会给出OP正在寻找的结果。

你实际上可以在 Python 中创建一个函数来模仿 JS 中的它,有点像这样,exec

import re

def exec(regex, s):
 m = re.search(regex, s)
 if (m):
  return [s for s in m.groups()]


arr = exec(r'(\w+ \w+ (".*?"|\S+) (".*?"|\S+))', 'add cmd item configname AAA 10.0.0.1 80 -option NONE -option2 YES -Option3 180')
print(arr)

这也提供了相同的输出并且是可重用的,因此很好的做事方式,

['add cmd item configname', 'item', 'configname']

最后,我很高兴通过评论进行健康的辩论,OP可以为这个问题找到一个可行的解决方案。

如果您随时遇到任何问题或有任何疑问,请随时告诉我。