正则表达式,以匹配重复字符的第一个实例

时间:2019-08-15 05:19:51

标签: r regex pcre

我的示例数据:

l1
[1] "xmms-1.2.11-x86_64-5"     "xmms-1.2.11-x86_64-6"    
[3] "xmodmap-1.0.10-x86_64-1"  "xmodmap-1.0.9-x86_64-1"  
[5] "xmodmap3-1.0.10-x86_64-1" "xmodmap3-1.0.9-x86_64-1"

我正在使用R,并且想要一个正则表达式,该正则表达式将仅捕获第一个破折号之前的字符。如

xmms
xmms
xmodmap
xmodmap
xmodmap3
xmodmap3

由于我使用的是R,因此正则表达式必须符合Perl。

我以为我可以使用破折号后面的表情来做到这一点,但是我只是得到了整个字符串的匹配项。这是我尝试过的模式: grepl("(?<=[a-z0-9])-",l1, perl=T),但它只匹配整个字符串。我想,如果我将第一个破折号作为捕获组,则可能可以使用后向,但我不知道如何使用后向和捕获组构建正则表达式。

我环顾了其他一些问题,以寻求可能的答案,似乎我需要一个非贪婪的符号?我尝试了grepl("(?<=[a-z0-9])-/.+?(?=-)/",l1, perl=T),但是那也不起作用。

对于如何捕获破折号前的第一组字符,我持开放态度。我目前在R的基础上,但是可以使用stringr之类的任何软件包都可以。

3 个答案:

答案 0 :(得分:3)

您也可以提取直到"-"第一次出现。使用基数R sub

sub("(.*?)-.*", "\\1", l)
#[1] "xmms"     "xmms"     "xmodmap"  "xmodmap"  "xmodmap3" "xmodmap3"

或与stringr::str_extract

stringr::str_extract(l, "(.*?)(?=-)")

数据

l <- c("xmms-1.2.11-x86_64-5","xmms-1.2.11-x86_64-6","xmodmap-1.0.10-x86_64-1",
  "xmodmap-1.0.9-x86_64-1","xmodmap3-1.0.10-x86_64-1" ,"xmodmap3-1.0.9-x86_64-1")

答案 1 :(得分:0)

1)基本R 选项是sub中的base R,以匹配-,后跟字符(.*),然后替换为空白(""

sub("-.*", "", l1)
#[1] "xmms"     "xmms"     "xmodmap"  "xmodmap"  "xmodmap3" "xmodmap3"

或分组捕获

sub("(\\w+).*", "\\1", l1)
#[1] "xmms"     "xmms"     "xmodmap"  "xmodmap"  "xmodmap3" "xmodmap3"

或与regmatches/regexpr

regmatches(l1, regexpr('\\w+', l1))
#[1] "xmms"     "xmms"     "xmodmap"  "xmodmap"  "xmodmap3" "xmodmap3"

或使用trimws

trimws(l1,  "right", whitespace = "-.*")
#[1] "xmms"     "xmms"     "xmodmap"  "xmodmap"  "xmodmap3" "xmodmap3"

或使用read.table

read.table(text = l1, sep="-", header = FALSE, stringsAsFactors = FALSE)$V1
#[1] "xmms"     "xmms"     "xmodmap"  "xmodmap"  "xmodmap3" "xmodmap3"

或带有strsplit

sapply(strsplit(l1, "-"), `[`, 1)

2)更严格,或者使用word中的stringr

library(stringr)
word(l1, 1, sep="-")

或与str_remove

str_remove(l1, "-.*")
#[1] "xmms"     "xmms"     "xmodmap"  "xmodmap"  "xmodmap3" "xmodmap3"

3)字符串或使用stri_extract_first中的stringi

library(stringi)
stri_extract_first(l1, regex = "\\w+")
#[1] "xmms"     "xmms"     "xmodmap"  "xmodmap"  "xmodmap3" "xmodmap3"

注意:grep/grepl用于检测字符串中的模式。要替换/提取子字符串,请在sub/regexpr/regmatches

中使用base R

数据

l1 <- c("xmms-1.2.11-x86_64-5", "xmms-1.2.11-x86_64-6", "xmodmap-1.0.10-x86_64-1", 
"xmodmap-1.0.9-x86_64-1", "xmodmap3-1.0.10-x86_64-1", "xmodmap3-1.0.9-x86_64-1"
)

答案 2 :(得分:0)

我想最简单的正则表达式可以满足您的需求

^[^-]+

匹配字符串(^)的开头和至少一个不是+-)的字符([^-])。

See it here at regex101

如果需要捕获它,请添加括号。

^([^-]+)