2017-07-18 150 views
3

提取物的话考虑一下这个简单的例子stringr:包含特定单词

dataframe <- data_frame(text = c('WAFF;WOFF;WIFF200;WIFF12', 
           'WUFF;WEFF;WIFF2;BIGWIFF')) 

> dataframe 
# A tibble: 2 x 1 
         text 
        <chr> 
1 WAFF;WOFF;WIFF200;WIFF12 
2 WUFF;WEFF;WIFF2;BIGWIFF 

在这里,我想提取含WIFF的话,那就是我想这样的

> output 
# A tibble: 2 x 1 
      text 
      <chr> 
1 WIFF200;WIFF12 
2 WIFF2;BIGWIFF 
一个数据帧落得

我试过使用

dataframe %>% 
    mutate(mystring = str_extract(text, regex('\bwiff\b', ignore_case=TRUE))) 

但这只能回调NA。有任何想法吗?

谢谢!

回答

2

您似乎要删除所有包含WIFF的单词以及尾随的;(如果有的话)。使用

> dataframedataframe <- data.frame(text = c('WAFF;WOFF;WIFF200;WIFF12', 'WUFF;WEFF;WIFF2;BIGWIFF')) 
> dataframe$text <- str_replace_all(dataframe$text, "(?i)\\b(?!\\w*WIFF)\\w+;?", "") 
> dataframe 
      text 
1 WIFF200;WIFF12 
2 WIFF2;BIGWIFF 

模式(?i)\\b(?!\\w*WIFF)\\w+;?比赛:

  • (?i) - 不区分大小写的在线修改
  • \\b - 一个字边界
  • (?!\\w*WIFF) - 负先行失败,其中一个字包含WIFF任何比赛它里面的任何地方
  • \\w+ - 1个或更多的字字符小号
  • ;? - 可选;?匹配1或者0次出现它修改模式)

如果你想使用str_extract某种原因,请注意您的正则表达式不能因为\bWIFF\b matches a whole word WIFF,没有别的工作。你的DF中没有这样的词汇。您可以使用"(?i)\\b\\w*WIFF\\w*\\b"WIFF里面(的情况下不区分大小写)匹配任何单词和使用str_extract_all获得多次出现,并且不要忘了比赛加入到一个单一的“串”:

> df <- data.frame(text = c('WAFF;WOFF;WIFF200;WIFF12', 'WUFF;WEFF;WIFF2;BIGWIFF')) 
> res <- str_extract_all(df$text, "(?i)\\b\\w*WIFF\\w*\\b") 
> res 
[[1]] 
[1] "WIFF200" "WIFF12" 

[[2]] 
[1] "WIFF2" "BIGWIFF" 

> df$text <- sapply(res, function(s) paste(s, collapse=';')) 
> df 
      text 
1 WIFF200;WIFF12 
2 WIFF2;BIGWIFF 

您可能会“缩水”将代码str_extract_all放入sapply函数中,我将它们分开以获得更好的可见性。

+0

感谢Wiktor的很不错。你似乎意味着更换不匹配的模式比提取匹配的模式更容易?为什么? –

+1

@诺比:我没有那样说。由您决定什么更容易。 –

+0

我的意思是你的解决方案很好,但是你知道我的'str_extract'根本不起作用吗? –

3

通过基础R经典之作,非正则表达式的方法是,

sapply(strsplit(me$text, ';', fixed = TRUE), function(i) 
           paste(grep('WIFF', i, value = TRUE, fixed = TRUE), collapse = ';')) 

#[1] "WIFF200;WIFF12" "WIFF2;BIGWIFF" 
+1

好棒;基地R.谢谢! –