考虑以下字符串:
x = "a (b, c), d [e, f (g, h)], i (j, k (l (m, n [o, p])))"
Run Code Online (Sandbox Code Playgroud)
我的目标是获取该字符串并将其转换为以下列表:
list("a" = list("b", "c"),
"d" = list("e", "f" = list("g", "h")),
"i" = list("j", "k" = list("l" = list("m", "n" = list("o", "p")))))
$a
$a[[1]]
[1] "b"
$a[[2]]
[1] "c"
$d
$d[[1]]
[1] "e"
$d$f
$d$f[[1]]
[1] "g"
$d$f[[2]]
[1] "h"
$i
$i[[1]]
[1] "j"
$i$k
$i$k$l
$i$k$l[[1]]
[1] "m"
$i$k$l$n
$i$k$l$n[[1]]
[1] "o"
$i$k$l$n[[2]]
[1] "p"
Run Code Online (Sandbox Code Playgroud)
第一个问题是尝试分离每个组件:
x = "a (b, c), d [e, f (g, h)], i (j, k (l (m, n [o, p])))"
str_split_quotes = function(s) {
o = el(strsplit(s, split = "(?<=\\)|\\]),", perl = T))
lapply(o, function(z) gsub(pattern = " ", "", z))
}
str_unparse_level = function(s) {
check_parsed = function(s) {
grepl("\\)|\\]", s)
}
parse = function(s) {
if (check_parsed(s)) {
substring_name = substr(s, 1, 1)
substring_content = substr(s, 3, nchar(s) - 1)
substring_content_split = el(strsplit(substring_content, ",(?![^()]*+\\))", perl = T))
o = list(substring_content_split)
names(o) = substring_name
return(o)}
else {return(s)}
}
lapply(s, parse)
}
str_unparse_level(str_split_quotes(x))
[[1]]
[[1]]$a
[1] "b" "c"
[[2]]
[[2]]$d
[1] "e" "f(g,h)"
[[3]]
[[3]]$i
[1] "j" "k(l(m,n[o,p]))"
Run Code Online (Sandbox Code Playgroud)
直观地说,这里需要发生的是,需要在这里执行某种涉及递归的函数(由于括号/括号的嵌套深度可变),以便可以创建一个列表,正如我在上面寻求的那样。鉴于我很少使用递归,我不清楚如何解决这个问题。
eval(parse一个选项是修改(and[后使用list
out <- eval(parse(text = gsub('(\\w+)', '"\\1"',
paste0("list(", gsub("\\(", "=list(", chartr("[]", "()", x)),
")"))))
Run Code Online (Sandbox Code Playgroud)
-检查OP的输出
> op_out <- list("a" = list("b", "c"),
+ "d" = list("e", "f" = list("g", "h")),
+ "i" = list("j", "k" = list("l" = list("m", "n" = list("o", "p")))))
> all.equal(out, op_out)
[1] TRUE
Run Code Online (Sandbox Code Playgroud)