Как я могу использовать обратные ссылки с `grep` в R? - PullRequest
15 голосов
/ 01 июня 2011

Я ищу элегантный способ возврата обратных ссылок с использованием регулярных выражений в R. Позвольте мне объяснить:

Допустим, я хочу найти строки, которые начинаются с названия месяца:

x <- c("May, 1, 2011", "30 June 2011")
grep("May|^June", x, value=TRUE)
[1] "May, 1, 2011"

Это работает, но я действительно хочу выделить месяц (т. Е. "Май", а не всю совпавшую строку.

Таким образом, можно использовать gsub, чтобы вернуть обратную ссылку, используя substituteПараметр. Но это имеет две проблемы:

  1. Вы должны обернуть шаблон внутри ". * (pattern). *)", чтобы подстановка произошла во всей строке.
  2. Вместо того, чтобы возвращать NA для несопоставленных строк, gsub возвращает исходную строку.Это явно не то, что я хочу:

Код и результаты:

gsub(".*(^May|^June).*", "\\1", x) 
[1] "May"          "30 June 2011"

Я мог бы, вероятно, кодировать обходной путь, выполняя все виды дополнительных проверок, но это быстро становится оченьгрязный.

Чтобы быть кристально чистым, желаемые результаты должны быть:

[1] "May"          NA

Есть ли простой способ достичь этого?

Ответы [ 3 ]

20 голосов
/ 01 июня 2011

regexpr аналогично grep, но возвращает позицию и длину (первого) совпадения в каждой строке:

> x <- c("May, 1, 2011", "30 June 2011", "June 2012")
> m <- regexpr("May|^June", x)
> m
[1]  1 -1  1
attr(,"match.length")
[1]  3 -1  4

Это означает, что первая строка имеет совпадение длины 3начиная с позиции 1, вторая строка не имеет соответствия, а третья строка имеет соответствие длины 4 в позиции 1.

Чтобы извлечь совпадения, вы можете использовать что-то вроде:

> m[m < 0] = NA
> substr(x, m, m + attr(m, "match.length") - 1)
[1] "May"  NA     "June"
9 голосов
/ 01 июня 2011

Пакет stringr имеет функцию именно для этой цели:

library(stringr)
x <- c("May, 1, 2011", "30 June 2011", "June 2012")
str_extract(x, "May|^June")
# [1] "May"  NA     "June"

Это довольно тонкая оболочка для regexpr, но stringr обычно облегчает обработку строк, будучи более согласованным, чем базаФункции R.

3 голосов
/ 01 июня 2011

Пакет gsubfn является более общим, чем функции grep и regexpr, и в нем есть способы для возврата обратных ссылок, см. Функцию strapply.

...