0

我正在尝试从 R 中获取完整的 RegEx 匹配,但我似乎只能获取字符串的第一部分。

使用http://regexpal.com/我可以确认我的 RegEx 是好的并且它符合我的期望。在我的数据中,“错误类型”位于星号前面的数字和下一个逗号之间。所以我希望"*20508436572 access forbidden by rule"在第一个实例和"*20508436572 some_error"第二个实例中返回。

例子:

library(stringr)

regex.errortype<-'\\*\\d+\\s[^,\\n]+'
test_string1<-'2014/08/07 08:28:56 [error] 21278#0: *20508436572 access forbidden by rule, client: 111.222.111.222'
test_string2<-'2014/08/07 08:28:56 [error] 21278#0: *20508436572 some_error, client: 111.222.111.222'

str_extract(test_string1, regex.errortype)
str_extract_all(test_string1, regex.errortype)
regmatches(test_string, regexpr(regex.errortype, test_string1))

str_extract(test_string2, regex.errortype)
str_extract_all(test_string2, regex.errortype)
regmatches(test_string2, regexpr(regex.errortype, test_string2))

结果:

> str_extract(test_string1, regex.errortype)
[1] "*20508436572 access forbidde"
> str_extract_all(test_string1, regex.errortype)
[[1]]
[1] "*20508436572 access forbidde"

> regmatches(test_string1, regexpr(regex.errortype, test_string1))
[1] "*20508436572 access forbidde"

> str_extract(test_string2, regex.errortype)
[1] "*20508436572 some_error"
> str_extract_all(test_string2, regex.errortype)
[[1]]
[1] "*20508436572 some_error"

> regmatches(test_string2, regexpr(regex.errortype, test_string2))
[1] "*20508436572 some_error"

如您所见,较长的匹配被截断,但较短的匹配被正确解析。

我在这里遗漏了什么,还是有其他方法可以恢复完整的比赛?

干杯,

安迪。

4

2 回答 2

2
 str_extract_all(test_string1, perl("(?<=\\#[0-9]\\: )\\*\\d+\\s[^,\\n]+"))[[1]]
#[1] "*20508436572 access forbidden by rule"

str_extract_all(test_string2, perl("(?<=\\#[0-9]\\: )\\*\\d+\\s[^,\\n]+"))[[1]]
#[1] "*20508436572 some_error"

使用 Lookbehind

(?<=\\#寻找#

[0-9] 后跟一个数字

\\: 后跟:一个空格

然后使用你的模式

于 2014-08-08T10:34:15.743 回答
0

这是一种gsub在两种情况下都删除所需字符串的方法,而无需重新编写正则表达式。

> gsub("((.*)[*])|([,](.*))", "", c(test_string1, test_string2))
# [1] "20508436572 access forbidden by rule" 
# [2] "20508436572 some_error"   

在正则表达式((.*)[*])|([,](.*))中,

  • ((.*)[*])删除直到*角色的所有内容。
  • |意思是“或”
  • ([,](.*))删除逗号,以及它之后的所有内容。
于 2014-08-08T10:49:14.503 回答