为什么我需要在执行 map(str_match_all()) 之后将我的数据框索引到 map()?
Why do I need to index my data frame to map() after doing map(str_match_all())?
我正在尝试解析包含字符串的数据框以提取最大值(数字),但遇到了一些问题。
如果我以这样的小标题开头:
tester <- tibble("phyloP46way_primate" = c(".{9}", "0.055{1}0.064{3}", "0.225{1}", "0.271{1}", "-0.706{1}-0.708{1}0.248{3}0.298{3}"))
然后使用 map()
或 modify()
应用 str_match_all()
从每个字符向量中挑选出值,我得到一个小标题(对于 modify()
) 5 个观察值(每个都是对 str_match_all()
的 5 次调用返回的字符矩阵列表)(或包含 5 个字符矩阵列表的 1 列表(对于 map()
)。
regex ≤- "(?:(?:-?\d+\.?\d+?)|\.)(?=(?:\{\d+\}|;|$))"
> str(foo_tbl<- tester %>% modify(str_match_all, pattern = regex))
Classes 'tbl_df', 'tbl' and 'data.frame': 5 obs. of 1 variable:
$ phyloP46way_primate:List of 5
..$ : chr [1, 1] "."
..$ : chr [1:2, 1] "0.055" "0.064"
..$ : chr [1, 1] "0.225"
..$ : chr [1, 1] "0.271"
..$ : chr [1:4, 1] "-0.706" "-0.708" "0.248" "0.298"
> str(foo_list<- tester %>% map(str_match_all, pattern = regex))
List of 1
$ phyloP46way_primate:List of 5
..$ : chr [1, 1] "."
..$ : chr [1:2, 1] "0.055" "0.064"
..$ : chr [1, 1] "0.225"
..$ : chr [1, 1] "0.271"
..$ : chr [1:4, 1] "-0.706" "-0.708" "0.248" "0.298"
现在,我想要做的是对这些“行”中的每一行应用一个函数。但是当我尝试映射时,它似乎只是将它们全部连接到一个向量中,然后从整个批次中选择单个最大值,而不是 one/row:
> map(foo_tbl, function(x) list_to_max(x))
$phyloP46way_primate
$phyloP46way_primate[[1]]
[1] "0.298"
除非我做一些奇怪的索引并映射到 foo_tbl[[1]]
而不是 foo_tbl
:
map(foo_tbl[[1]], function(x) list_to_max(x)) %>% unlist()
[1] "." "0.064" "0.225" "0.271" "0.298"
我认为我的 list_to_max()
一定在做意想不到的事情,因为它们的行为符合我的预期:
> invisible(map(foo_tbl, function(x) print(paste0("x is: ", x))))
[1] "x is: ."
[2] "x is: c(\"0.055\", \"0.064\")"
[3] "x is: 0.225"
[4] "x is: 0.271"
[5] "x is: c(\"-0.706\", \"-0.708\", \"0.248\", \"0.298\")"
> invisible(modify(foo_tbl, function(x) print(paste0("x is: ", x))))
[1] "x is: ."
[2] "x is: c(\"0.055\", \"0.064\")"
[3] "x is: 0.225"
[4] "x is: 0.271"
[5] "x is: c(\"-0.706\", \"-0.708\", \"0.248\", \"0.298\")"
这是我的函数:
list_to_max <- function(character_vector) {
numbers <- suppressWarnings(as.numeric(character_vector))
if (all(is.na(numbers))) {
return(".")
} else {
numbers %>% max(., na.rm = TRUE) %>% toString()
}
}
toString
会将所有内容强制转换为逗号分隔的字符串,这不是很有用。这是一个将所有内容都保留在原始 data.frame:
中的工作流程
library(tidyverse)
tester <- tibble("phyloP46way_primate" = c(".{9}", "0.055{1}0.064{3}", "0.225{1}", "0.271{1}", "-0.706{1}-0.708{1}0.248{3}0.298{3}"))
tester %>%
mutate(p_clean = gsub('\{.*?\}', ' ', phyloP46way_primate),
p_list = strsplit(p_clean, '\s+'),
p_list = map(p_list, as.numeric),
p_max = map_dbl(p_list, max))
#> # A tibble: 5 x 4
#> phyloP46way_primate p_clean p_list p_max
#> <chr> <chr> <list> <dbl>
#> 1 .{9} . <dbl [1]> NA
#> 2 0.055{1}0.064{3} 0.055 0.064 <dbl [2]> 0.064
#> 3 0.225{1} 0.225 <dbl [1]> 0.225
#> 4 0.271{1} 0.271 <dbl [1]> 0.271
#> 5 -0.706{1}-0.708{1}0.248{3}0.298{3} -0.706 -0.708 0.248 0.298 <dbl [4]> 0.298
我正在尝试解析包含字符串的数据框以提取最大值(数字),但遇到了一些问题。
如果我以这样的小标题开头:
tester <- tibble("phyloP46way_primate" = c(".{9}", "0.055{1}0.064{3}", "0.225{1}", "0.271{1}", "-0.706{1}-0.708{1}0.248{3}0.298{3}"))
然后使用 map()
或 modify()
应用 str_match_all()
从每个字符向量中挑选出值,我得到一个小标题(对于 modify()
) 5 个观察值(每个都是对 str_match_all()
的 5 次调用返回的字符矩阵列表)(或包含 5 个字符矩阵列表的 1 列表(对于 map()
)。
regex ≤- "(?:(?:-?\d+\.?\d+?)|\.)(?=(?:\{\d+\}|;|$))"
> str(foo_tbl<- tester %>% modify(str_match_all, pattern = regex))
Classes 'tbl_df', 'tbl' and 'data.frame': 5 obs. of 1 variable:
$ phyloP46way_primate:List of 5
..$ : chr [1, 1] "."
..$ : chr [1:2, 1] "0.055" "0.064"
..$ : chr [1, 1] "0.225"
..$ : chr [1, 1] "0.271"
..$ : chr [1:4, 1] "-0.706" "-0.708" "0.248" "0.298"
> str(foo_list<- tester %>% map(str_match_all, pattern = regex))
List of 1
$ phyloP46way_primate:List of 5
..$ : chr [1, 1] "."
..$ : chr [1:2, 1] "0.055" "0.064"
..$ : chr [1, 1] "0.225"
..$ : chr [1, 1] "0.271"
..$ : chr [1:4, 1] "-0.706" "-0.708" "0.248" "0.298"
现在,我想要做的是对这些“行”中的每一行应用一个函数。但是当我尝试映射时,它似乎只是将它们全部连接到一个向量中,然后从整个批次中选择单个最大值,而不是 one/row:
> map(foo_tbl, function(x) list_to_max(x))
$phyloP46way_primate
$phyloP46way_primate[[1]]
[1] "0.298"
除非我做一些奇怪的索引并映射到 foo_tbl[[1]]
而不是 foo_tbl
:
map(foo_tbl[[1]], function(x) list_to_max(x)) %>% unlist()
[1] "." "0.064" "0.225" "0.271" "0.298"
我认为我的 list_to_max()
一定在做意想不到的事情,因为它们的行为符合我的预期:
> invisible(map(foo_tbl, function(x) print(paste0("x is: ", x))))
[1] "x is: ."
[2] "x is: c(\"0.055\", \"0.064\")"
[3] "x is: 0.225"
[4] "x is: 0.271"
[5] "x is: c(\"-0.706\", \"-0.708\", \"0.248\", \"0.298\")"
> invisible(modify(foo_tbl, function(x) print(paste0("x is: ", x))))
[1] "x is: ."
[2] "x is: c(\"0.055\", \"0.064\")"
[3] "x is: 0.225"
[4] "x is: 0.271"
[5] "x is: c(\"-0.706\", \"-0.708\", \"0.248\", \"0.298\")"
这是我的函数:
list_to_max <- function(character_vector) {
numbers <- suppressWarnings(as.numeric(character_vector))
if (all(is.na(numbers))) {
return(".")
} else {
numbers %>% max(., na.rm = TRUE) %>% toString()
}
}
toString
会将所有内容强制转换为逗号分隔的字符串,这不是很有用。这是一个将所有内容都保留在原始 data.frame:
library(tidyverse)
tester <- tibble("phyloP46way_primate" = c(".{9}", "0.055{1}0.064{3}", "0.225{1}", "0.271{1}", "-0.706{1}-0.708{1}0.248{3}0.298{3}"))
tester %>%
mutate(p_clean = gsub('\{.*?\}', ' ', phyloP46way_primate),
p_list = strsplit(p_clean, '\s+'),
p_list = map(p_list, as.numeric),
p_max = map_dbl(p_list, max))
#> # A tibble: 5 x 4
#> phyloP46way_primate p_clean p_list p_max
#> <chr> <chr> <list> <dbl>
#> 1 .{9} . <dbl [1]> NA
#> 2 0.055{1}0.064{3} 0.055 0.064 <dbl [2]> 0.064
#> 3 0.225{1} 0.225 <dbl [1]> 0.225
#> 4 0.271{1} 0.271 <dbl [1]> 0.271
#> 5 -0.706{1}-0.708{1}0.248{3}0.298{3} -0.706 -0.708 0.248 0.298 <dbl [4]> 0.298