Обратная gsub

У меня есть HTML-код, с которым я работаю. Я хочу извлечь определенные строки.

Я хочу извлечь это из строки x предпочтительно используя базу R: coleman_l, SMOG4

Вот что у меня есть:

x <- "<code>(hi)<a href=\"Read\">auto</a></code>(coleman_l, SMOG4)<br />Read</li>" 
#remove the string (this works)
gsub("a></code>(.+?)<br", "a></code><br", x)

#> gsub("a></code>(.+?)<br", "a></code><br", x)
#[1] "<code>(hi)<a href=\"Read\">auto</a></code><br />Read</li>"

#attempt to extract that information (doesn't work)
re <- "(?<=a></code>().*?(?=)<br)"
regmatches(x, gregexpr(re, x, perl=TRUE))

Сообщение об ошибке:

> regmatches(x, gregexpr(re, x, perl=TRUE)) 
Error in gregexpr(re, x, perl = TRUE) : 
  invalid regular expression '(?<=a></code>().*?(?=)<br)'
In addition: Warning message:
In gregexpr(re, x, perl = TRUE) : PCRE pattern compilation error
        'lookbehind assertion is not fixed length'
        at ')'

    enter code here

ПРИМЕЧАНИЕ: помечено как регулярное выражение, но это регулярное выражение R.

3 ответа

Решение

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

x <- 
  "<code>(hi)<a href=\"Read\">auto</a></code>(coleman_l, SMOG4)<br />Read</li>" 
gsub(".*a></code>(.+?)<br.*", "\\1", x)
# [1] "(coleman_l, SMOG4)"

Если скобки также должны быть удалены, добавьте их к части "простого текста", которую вы связываете, чтобы соответствовать, но помните, что их нужно будет экранировать:

gsub(".*a></code>\\((.+?)\\)<br.*", "\\1", x)
# [1] "coleman_l, SMOG4"

FWIW, оригинальный подход OP, возможно, сработал с небольшой настройкой.

> x
[1] "<code>(hi)<a href=\"Read\">auto</a></code>(coleman_l, SMOG4)<br />Read</li>"
> re <- "(?<=a></code>\\().*?(?=\\)<br)"
> regmatches(x, gregexpr(re, x, perl=TRUE))
[[1]]
[1] "coleman_l, SMOG4"

Преимущество такого подхода по сравнению с другим предлагаемым решением состоит в том, что если существует возможность нескольких совпадений, то все они будут отображаться.

> x <- '<code>(hi)<a href=\"Read\">auto</a></code>(coleman_l, SMOG4)<br />Read</li><code>(hi)<a href=\"Read\">auto</a></code>(coleman_l_2, SMOG4_2)<br />Read</li>'
> regmatches(x, gregexpr(re, x, perl=TRUE))
[[1]]
[1] "coleman_l, SMOG4"     "coleman_l_2, SMOG4_2"

Это будет работать, несмотря на то, что уродливо.

x<-"<code>(hi)<a href=\"Read\">auto</a></code>(coleman_l, SMOG4)<br />Read</li>"

x2 <- gsub("^.+(\\(.+\\)).+\\((.+)\\).+$","\\2",x)
x2
[1] "coleman_l, SMOG4"
Другие вопросы по тегам