在给定替换列表的情况下搜索并替换数据框中的元素。
代码:
testing123tmp <- data.frame(x=c("it's", "not", "working"))
testing123tmp$x <- as.character(testing123tmp$x)
tmp <- list("it's" = "hey", "working"="dead")
apply(testing123tmp,2,function(x) gsubfn('.', tmp, x))
预期输出:
x
[1,] hey
[2,] not
[3,] dead
我目前的输出:
x
[1,] "it's"
[2,] "not"
[3,] "working"
一直在寻找chartr和gsub中可能的解决方案,但是想要简单(短编码),这样的操作需要多个gsub。此外,我的变量tmp可以缩放到多对替换,以便:
tmp <- list("it's" = "hey",
"working"="dead",
"other" = "other1",
.. = .. ,
.. = .. ,
.. = .. )
编辑/更新#1:
答案 0 :(得分:4)
问题是:
点只匹配一个字符,因此它永远不会匹配整个字符串,除非整个字符串有一个字符,因此tmp
中的名称不会匹配。使用".*"
匹配整个字符串。如果你想匹配单词,即在x
的每个组件中可能有几个由空格分隔的单词,那么例如x
的一个组件可能是"it's not"
,我们仍然希望匹配it's
然后使用"\\S+"
。还有其他可以想象的变化,这给出了一个包含其中许多变化的框架。
gsubfn
的第三个参数可能已经是一个向量,gsubfn
将迭代它,因此不必使用apply
。 (它仍然适用于apply
,但这是不必要的。)
将数据框中的所有内容放在一个简单的方法是使用transform
,如下所示(或者也可以在gsubfn包中使用transform2
)。 x
会自动引用x
数据框中的testing123tmp
列,而transform
将生成一个不会覆盖原始数据框的新数据框。如果您希望保留这些内容,请将transform
的结果分配给新名称,或者如果您要覆盖testing123tmp
,请将其分配回testing123tmp
。
我们可以使用stringsAsFactors = FALSE
来避免生成字符列。
testing123tmp <- data.frame(x=c("it's", "not", "working"), stringsAsFactors = FALSE)
因此我们可以将代码缩减为:
transform(testing123tmp, y = gsubfn(".*", tmp, x))
提供以下data.frame:
x y
1 it's hey
2 not not
3 working dead
如果我们要覆盖x
列而不是保留单独的输入和输出列,我们可以在x = ...
语句中使用transform
而不是y = ...
。
答案 1 :(得分:2)
你可以写
gsubfn(".*", tmp, testing123tmp$x)
# [1] "hey" "not" "dead"
然后
testing123tmp$x <- gsubfn(".*", tmp, testing123tmp$x)
至于您的方法,不需要apply
因为gsubfn
在该参数上进行了矢量化,问题是仅匹配.
---一个符号,而{ {1}}和it's
的长度各不相同。
但是,如果要用另一个单词替换一个单词,则不需要正则表达式。例如,
working
应该更快。如果任务涉及更多,那么我想
idx <- testing123tmp$x %in% names(tmp)
testing123tmp$x[idx] <- unlist(tmp)[testing123tmp$x[idx]]
应该比library(stringr)
str_replace_all(testing123tmp$x, unlist(tmp))
# [1] "hey" "not" "dead"
更强大,因为您不需要处理gsubfn
等模式。