当我尝试使用ddply
来总结data.frame的某些方面时,如果我只包含导致数字数据的表达式,那么事情就好了。但是,如果我包含导致数字和字符数据的表达式,那么所有输出列都会成为字符,我绝对没有预料到并且确实将我的代码放到了下游。这是我所谈论的可重复的例子:
library(plyr)
set.seed(1234)
data <- data.frame(x = 1:25,
y = c((1:25)*4 + rnorm(100, mean = 0, sd = 50),
(1:25)*4 + rnorm(100, mean = 0, sd = 1000)),
category = c(rep("stuff with a stronger correlation", 100),
rep("stuff with a weaker correlation", 100)))
lmresults <- ddply(data, "category", function(df) c(
slope = coef(lm(df$y ~ df$x))[2],
pval = signif(summary(lm(df$y ~ df$x))$coef[2, "Pr(>|t|)"], 2)
))
str(lmresults)
此输出:
'data.frame': 2 obs. of 3 variables:
$ category : Factor w/ 2 levels "stuff with a stronger correlation",..: 1 2
$ slope.df$x: num 4.15 12.31
$ pval : num 3.7e-09 3.7e-01
请注意&#34;斜坡&#34;和&#34; pval&#34;都是数字的。但是,如果我这样做:
lmresults2 <- ddply(data, "category", function(df) c(
pval = signif(summary(lm(df$y ~ df$x))$coef[2, "Pr(>|t|)"], 2),
slope = paste("slope =", signif(coef(lm(df$y ~ df$x))[2], 2))
))
str(lmresults2)
输出结果为:
'data.frame': 2 obs. of 3 variables:
$ category: Factor w/ 2 levels "stuff with a stronger correlation",..: 1 2
$ pval : chr "3.7e-09" "0.37"
$ slope : chr "slope = 4.1" "slope = 12"
我期待slope
成为角色,但突然pval
也是角色!
这是 plyr 中的错误吗?它是否将输出转换为矩阵,矩阵必须与所有数据具有相同的类?但如果是这样的话,为什么对象lmresults2
的类仍然是&#34; data.frame&#34;?
答案 0 :(得分:2)
不,这不是一个错误。这是因为您在匿名函数中使用c()
。根据{{1}}:
所有参数都被强制转换为公共类型,它是返回值的类型,
...
输出类型由层次结构中的最高类型的组件确定NULL&lt;原始&lt;逻辑&lt;整数&lt;双&lt;复杂&lt;字符&lt;列表&lt;表达
你的第一个匿名函数连接两个调用,这两个调用都会产生数值,因此没有问题。但是你的第二个匿名函数将用help(c)
创建的数字与由signif()
创建的字符连接起来,从而给出一个字符结果。
也许您想要paste()
而不是data.frame(pval = ..., slope = ...)
。为了更简单地了解发生了什么,请查看c()
的结果。它是数字还是字符?