提取具有两个以上字符并匹配模式的列表元素
Extract elements of a list with more than two characters and matching a pattern
我正在尝试查找一个列表的索引,其中一个元素与特定模式匹配并且 n 个字符>1,例如:
i = "a"
ll = list(c("a"), c("b", "abc"), c("cc", "b"), c("c", "b"), c("ac", "c"), c("a", "bc"))
我想提取 ll[[2]] 和 ll[[5]]。这种让我走上了正确的道路,但并不完全是因为我只想要包含模式并具有 nchar>1...
的元素
sapply(ll, function(x) sapply(x, function(x) nchar(x)>1 & grep(i, x)))
谢谢!!
ll[sapply(ll, function(x) any(ifelse(nchar(x) > 1, grepl("a", x), FALSE)))]
使用 tidyverse 包的解决方案。
library(purr)
library(stringr)
library(magrittr)
ll %>% map(function(x) x[any(nchar(x) > 1) & str_detect(x,"a")]) %>%
Filter(length,.)
我们可以使用Filter
。这个想法是找到那些具有 a
的元素,对这些元素进行子集化,检查这些元素是否具有 nchar
大于 1,用 any
包装它(如果每个 list
元素)和 Filter
它。
Filter(function(x) any(nchar(x[grep(i, x)])>1), ll)
#[[1]]
#[1] "b" "abc"
#[[2]]
#[1] "ac" "c"
或
Filter(function(x) any(nchar(grep(i, x, value = TRUE))>1), ll)
不使用 nchar
的稍微不同的方法会更多地利用正则表达式。
Has n characters>1
表示可以先有一些字符再有"a"或者"a"再有一些字符。作为正则表达式:"[[:alpha:]]a | a[[:alpha:]]"
。 |
表示 "or".
这导致:
Filter(function(x) any(grepl("[[:alpha:]]a|a[[:alpha:]]", x)), ll)
另一个更通用的选项是使用 lookahaeds (~AND),如下所示:
Filter(function(x) any(grepl("(?=[[:alpha:]]{2,})(?=a)", x, perl=TRUE)), ll)
其中 [[:alpha:]]{2,}
表示至少 2 个字母字符 = A-Za-z
a
意味着它需要有一个 a
。参见 Regular Expressions: Is there an AND operator?
编辑:
您始终可以使用 paste
或 sprintf
"build" 这些正则表达式,如下所示:
i="a"
sprintf("(?=[[:alpha:]]{2,})(?=%s)", i) # Second solution
总的来说是这样的
Filter(function(x) any(grepl(sprintf("(?=[[:alpha:]]{2,})(?=%s)", i), x, perl=TRUE)), ll)
我正在尝试查找一个列表的索引,其中一个元素与特定模式匹配并且 n 个字符>1,例如:
i = "a"
ll = list(c("a"), c("b", "abc"), c("cc", "b"), c("c", "b"), c("ac", "c"), c("a", "bc"))
我想提取 ll[[2]] 和 ll[[5]]。这种让我走上了正确的道路,但并不完全是因为我只想要包含模式并具有 nchar>1...
的元素sapply(ll, function(x) sapply(x, function(x) nchar(x)>1 & grep(i, x)))
谢谢!!
ll[sapply(ll, function(x) any(ifelse(nchar(x) > 1, grepl("a", x), FALSE)))]
使用 tidyverse 包的解决方案。
library(purr)
library(stringr)
library(magrittr)
ll %>% map(function(x) x[any(nchar(x) > 1) & str_detect(x,"a")]) %>%
Filter(length,.)
我们可以使用Filter
。这个想法是找到那些具有 a
的元素,对这些元素进行子集化,检查这些元素是否具有 nchar
大于 1,用 any
包装它(如果每个 list
元素)和 Filter
它。
Filter(function(x) any(nchar(x[grep(i, x)])>1), ll)
#[[1]]
#[1] "b" "abc"
#[[2]]
#[1] "ac" "c"
或
Filter(function(x) any(nchar(grep(i, x, value = TRUE))>1), ll)
不使用 nchar
的稍微不同的方法会更多地利用正则表达式。
Has n characters>1
表示可以先有一些字符再有"a"或者"a"再有一些字符。作为正则表达式:"[[:alpha:]]a | a[[:alpha:]]"
。 |
表示 "or".
这导致:
Filter(function(x) any(grepl("[[:alpha:]]a|a[[:alpha:]]", x)), ll)
另一个更通用的选项是使用 lookahaeds (~AND),如下所示:
Filter(function(x) any(grepl("(?=[[:alpha:]]{2,})(?=a)", x, perl=TRUE)), ll)
其中 [[:alpha:]]{2,}
表示至少 2 个字母字符 = A-Za-z
a
意味着它需要有一个 a
。参见 Regular Expressions: Is there an AND operator?
编辑:
您始终可以使用 paste
或 sprintf
"build" 这些正则表达式,如下所示:
i="a"
sprintf("(?=[[:alpha:]]{2,})(?=%s)", i) # Second solution
总的来说是这样的
Filter(function(x) any(grepl(sprintf("(?=[[:alpha:]]{2,})(?=%s)", i), x, perl=TRUE)), ll)