为了分享R的更多提示和技巧,您最有用的功能或技巧是什么?聪明的矢量化?数据输入/输出?可视化和图形?统计分析?特殊功能?互动环境本身?
每个帖子一个项目,我们将看看我们是否通过投票获得了胜利。
[编辑2008年8月25日]:所以一周之后,似乎简单的str()
赢得了民意调查。因为我想自己推荐一个,这是一个容易接受的答案。
答案 0 :(得分:64)
str()
告诉你任何对象的结构。
答案 1 :(得分:64)
我经常使用的一个非常有用的函数是dput(),它允许你以R代码的形式转储对象。
# Use the iris data set
R> data(iris)
# dput of a numeric vector
R> dput(iris$Petal.Length)
c(1.4, 1.4, 1.3, 1.5, 1.4, 1.7, 1.4, 1.5, 1.4, 1.5, 1.5, 1.6,
1.4, 1.1, 1.2, 1.5, 1.3, 1.4, 1.7, 1.5, 1.7, 1.5, 1, 1.7, 1.9,
1.6, 1.6, 1.5, 1.4, 1.6, 1.6, 1.5, 1.5, 1.4, 1.5, 1.2, 1.3, 1.4,
1.3, 1.5, 1.3, 1.3, 1.3, 1.6, 1.9, 1.4, 1.6, 1.4, 1.5, 1.4, 4.7,
4.5, 4.9, 4, 4.6, 4.5, 4.7, 3.3, 4.6, 3.9, 3.5, 4.2, 4, 4.7,
3.6, 4.4, 4.5, 4.1, 4.5, 3.9, 4.8, 4, 4.9, 4.7, 4.3, 4.4, 4.8,
5, 4.5, 3.5, 3.8, 3.7, 3.9, 5.1, 4.5, 4.5, 4.7, 4.4, 4.1, 4,
4.4, 4.6, 4, 3.3, 4.2, 4.2, 4.2, 4.3, 3, 4.1, 6, 5.1, 5.9, 5.6,
5.8, 6.6, 4.5, 6.3, 5.8, 6.1, 5.1, 5.3, 5.5, 5, 5.1, 5.3, 5.5,
6.7, 6.9, 5, 5.7, 4.9, 6.7, 4.9, 5.7, 6, 4.8, 4.9, 5.6, 5.8,
6.1, 6.4, 5.6, 5.1, 5.6, 6.1, 5.6, 5.5, 4.8, 5.4, 5.6, 5.1, 5.1,
5.9, 5.7, 5.2, 5, 5.2, 5.4, 5.1)
# dput of a factor levels
R> dput(levels(iris$Species))
c("setosa", "versicolor", "virginica")
在您寻求帮助时,发布易于重现的数据块,或者编辑或重新排序因子的级别,这非常有用。
答案 2 :(得分:42)
head()和tail()来获取数据帧,向量,矩阵,函数等的第一个和最后一个部分。特别是对于大数据帧,这是检查它已加载好的快速方法。
答案 3 :(得分:38)
一个不错的功能:读取数据使用 连接 ,可以是本地文件,通过http访问的远程文件,来自其他程序的管道或更多。
作为一个简单的例子,考虑从random.org(基于大气噪声而不是伪随机数发生器提供真随机数)的min = 100和max = 200之间的N = 10个随机整数的这种访问:
R> site <- "http://random.org/integers/" # base URL
R> query <- "num=10&min=100&max=200&col=2&base=10&format=plain&rnd=new"
R> txt <- paste(site, query, sep="?") # concat url and query string
R> nums <- read.table(file=txt) # and read the data
R> nums # and show it
V1 V2
1 165 143
2 107 118
3 103 132
4 191 100
5 138 185
R>
另外,random包提供了几个便于访问random.org的便利功能。
答案 4 :(得分:35)
我发现我越来越多地使用with()
和within()
。不再有$
乱丢我的代码而且不需要开始将对象附加到搜索路径。更严重的是,我发现with()
等使我的数据分析脚本的意图更加清晰。
> df <- data.frame(A = runif(10), B = rnorm(10))
> A <- 1:10 ## something else hanging around...
> with(df, A + B) ## I know this will use A in df!
[1] 0.04334784 -0.40444686 1.99368816 0.13871605 -1.17734837
[6] 0.42473812 2.33014226 1.61690799 1.41901860 0.8699079
with()
设置一个评估R表达式的环境。 within()
执行相同的操作,但允许您修改用于创建环境的数据对象。
> df <- within(df, C <- rpois(10, lambda = 2))
> head(df)
A B C
1 0.62635571 -0.5830079 1
2 0.04810539 -0.4525522 1
3 0.39706979 1.5966184 3
4 0.95802501 -0.8193090 2
5 0.76772541 -1.9450738 2
6 0.21335006 0.2113881 4
我第一次使用within()
时没有意识到的一点是你必须做一个赋值作为表达式的一部分和分配返回的对象(如上所述)来获取期望的效果。
答案 5 :(得分:34)
http://www.omegahat.org/RGoogleDocs/
我发现Google电子表格是所有合作者在同一页面上的绝佳方式。此外,Google表单允许用户从受访者处获取数据,并毫不费力地将其写入Google电子表格。由于数据经常变化并且几乎从不是最终的,因此R直接阅读谷歌电子表格比下载csv文件并阅读它们更为可取。
# Get data from google spreadsheet
library(RGoogleDocs)
ps <-readline(prompt="get the password in ")
auth = getGoogleAuth("me@gmail.com", ps, service="wise")
sheets.con <- getGoogleDocsConnection(auth)
ts2=getWorksheets("Data Collection Repos",sheets.con)
names(ts2)
init.consent <-sheetAsMatrix(ts2$Sheet1,header=TRUE, as.data.frame=TRUE, trim=TRUE)
除了以下一两个命令需要几秒钟之后,我无法记住。
getGoogleAuth
getGoogleDocsConnection
getWorksheets
答案 6 :(得分:27)
使用反引号来引用非标准名称。
> df <- data.frame(x=rnorm(5),y=runif(5))
> names(df) <- 1:2
> df
1 2
1 -1.2035003 0.6989573
2 -1.2146266 0.8272276
3 0.3563335 0.0947696
4 -0.4372646 0.9765767
5 -0.9952423 0.6477714
> df$1
Error: unexpected numeric constant in "df$1"
> df$`1`
[1] -1.2035003 -1.2146266 0.3563335 -0.4372646 -0.9952423
在这种情况下,df [,“1”]也可以。但是后面的方法在公式内工作!
> lm(`2`~`1`,data=df)
Call:
lm(formula = `2` ~ `1`, data = df)
Coefficients:
(Intercept) `1`
0.4087 -0.3440
[编辑] 德克问为什么会给出无效的名字?我不知道!但我确实经常在实践中遇到这个问题。例如,使用hadley的重塑包:
> library(reshape)
> df$z <- c(1,1,2,2,2)
> recast(df,z~.,id.var="z")
Aggregation requires fun.aggregate: length used as default
z (all)
1 1 4
2 2 6
> recast(df,z~.,id.var="z")$(all)
Error: unexpected '(' in "recast(df,z~.,id.var="z")$("
> recast(df,z~.,id.var="z")$`(all)`
Aggregation requires fun.aggregate: length used as default
[1] 4 6
答案 7 :(得分:25)
不知道这是多么出名,但是我肯定会利用的是环境的传递功能。
zz <- new.env()
zz$foo <- c(1,2,3,4,5)
changer <- function(blah) {
blah$foo <- 5
}
changer(zz)
zz$foo
对于这个例子来说,为什么它有用是没有意义的,但是如果你在它周围传递大型物体可以提供帮助。
答案 8 :(得分:23)
我最喜欢的是foreach库。它可以让你完成所有不错的应用程序,但语法更简单:
list_powers <- foreach(i = 1:100) %do% {
lp <- x[i]^i
return (lp)
}
最好的部分是,如果您正在做一些实际需要大量时间的事情,您可以从%do%
切换到%dopar%
(使用适当的后端库)以立即并行化,甚至跨越一个集群。非常光滑。
答案 9 :(得分:19)
我做了很多基本的数据操作,所以这里有两个内置函数(转换,子集)和一个库( sqldf 强烈>)我每天都在使用。
sales <- expand.grid(country = c('USA', 'UK', 'FR'),
product = c(1, 2, 3))
sales$revenue <- rnorm(dim(sales)[1], mean=100, sd=10)
> sales
country product revenue
1 USA 1 108.45965
2 UK 1 97.07981
3 FR 1 99.66225
4 USA 2 100.34754
5 UK 2 87.12262
6 FR 2 112.86084
7 USA 3 95.87880
8 UK 3 96.43581
9 FR 3 94.59259
## transform currency to euros
usd2eur <- 1.434
transform(sales, euro = revenue * usd2eur)
>
country product revenue euro
1 USA 1 108.45965 155.5311
2 UK 1 97.07981 139.2125
3 FR 1 99.66225 142.9157
...
subset(sales,
country == 'USA' & product %in% c(1, 2),
select = c('product', 'revenue'))
>
product revenue
1 1 108.4597
4 2 100.3475
sqldf package为R数据帧提供SQL接口
## recast the previous subset() expression in SQL
sqldf('SELECT product, revenue FROM sales \
WHERE country = "USA" \
AND product IN (1,2)')
>
product revenue
1 1 108.4597
2 2 100.3475
执行聚合或GROUP BY
sqldf('select country, sum(revenue) revenue \
FROM sales \
GROUP BY country')
>
country revenue
1 FR 307.1157
2 UK 280.6382
3 USA 304.6860
对于数据帧上更复杂的类似map-reduce的功能,请查看plyr包。如果发现自己想要脱掉头发,我建议您查看Data Manipulation with R。
答案 10 :(得分:18)
?ave
'x []'的子集被平均,其中每个子集由这些子集组成 具有相同因子水平的观察。 用法: ave(x,...,FUN = mean)
我一直都在使用它。 (例如in this answer here at so)
答案 11 :(得分:18)
一种加速代码并消除for循环的方法。
而不是循环遍历数据框寻找值的循环。 只需使用这些值的df的一部分,就会快得多。
所以代替:
for(i in 1:nrow(df)){
if (df$column[i] == x) {
df$column2[i] <- y
or any other similiar code
}
}
做这样的事情:
df$column2[df$column1 == x] <- y
基本概念非常经常适用,是摆脱for循环的好方法
答案 12 :(得分:16)
在R编程(非交互式会话)中,我使用if (bad.condition) stop("message")
a lot 。每个函数都从其中的一些函数开始,当我完成计算时,我也将它们加入其中。我想我习惯于在C中使用assert()
。这样做的好处是双重的。首先,使用这些检查来获得工作代码要快得多。其次,也许更重要的是,当你在编辑器的每个屏幕上看到这些检查时,使用现有代码要容易得多。你不必怀疑是x>0
,还是相信评论说它是......你将知道,一目了然,它就是。
PS。我的第一篇文章。要温柔!
答案 13 :(得分:16)
有时您需要rbind
多个数据框。 do.call()
会让你这样做(当我问这个问题时,有人必须向我解释这个问题,因为它似乎没有明显的用途。)
foo <- list()
foo[[1]] <- data.frame(a=1:5, b=11:15)
foo[[2]] <- data.frame(a=101:105, b=111:115)
foo[[3]] <- data.frame(a=200:210, b=300:310)
do.call(rbind, foo)
答案 14 :(得分:13)
当你在某个地方出现错误并且不易理解时,traceback()
函数是必须的。它将打印堆栈的跟踪,非常有用,因为R默认情况下不是很冗长。
然后设置options(error=recover)
将允许您“输入”引发错误的函数并尝试理解究竟发生了什么,就像您完全控制它并可以在其中放置browser()
一样
这三个函数可以真正帮助调试代码。
答案 15 :(得分:12)
我真的很惊讶没有人发布关于申请,申请,lapply和sapply。我在R中做东西时使用的一般规则是,如果我有一个正在进行数据处理或模拟的for循环,我会尝试将其分解并用* apply替换它。有些人回避* apply函数,因为他们认为只能传入单个参数函数。没有什么可以进一步说实话!就像在Javascript中传递具有参数作为第一类对象的函数一样,您可以在R中使用匿名函数执行此操作。例如:
> sapply(rnorm(100, 0, 1), round)
[1] 1 1 0 1 1 -1 -2 0 2 2 -2 -1 0 1 -1 0 1 -1 0 -1 0 0 0 0 0
[26] 2 0 -1 -2 0 0 1 -1 1 5 1 -1 0 1 1 1 2 0 -1 1 -1 1 0 -1 1
[51] 2 1 1 -2 -1 0 -1 2 -1 1 -1 1 -1 0 -1 -2 1 1 0 -1 -1 1 1 2 0
[76] 0 0 0 -2 -1 1 1 -2 1 -1 1 1 1 0 0 0 -1 -3 0 -1 0 0 0 1 1
> sapply(rnorm(100, 0, 1), round(x, 2)) # How can we pass a parameter?
Error in match.fun(FUN) : object 'x' not found
# Wrap your function call in an anonymous function to use parameters
> sapply(rnorm(100, 0, 1), function(x) {round(x, 2)})
[1] -0.05 -1.74 -0.09 -1.23 0.69 -1.43 0.76 0.55 0.96 -0.47 -0.81 -0.47
[13] 0.27 0.32 0.47 -1.28 -1.44 -1.93 0.51 -0.82 -0.06 -1.41 1.23 -0.26
[25] 0.22 -0.04 -2.17 0.60 -0.10 -0.92 0.13 2.62 1.03 -1.33 -1.73 -0.08
[37] 0.45 -0.93 0.40 0.05 1.09 -1.23 -0.35 0.62 0.01 -1.08 1.70 -1.27
[49] 0.55 0.60 -1.46 1.08 -1.88 -0.15 0.21 0.06 0.53 -1.16 -2.13 -0.03
[61] 0.33 -1.07 0.98 0.62 -0.01 -0.53 -1.17 -0.28 -0.95 0.71 -0.58 -0.03
[73] -1.47 -0.75 -0.54 0.42 -1.63 0.05 -1.90 0.40 -0.01 0.14 -1.58 1.37
[85] -1.00 -0.90 1.69 -0.11 -2.19 -0.74 1.34 -0.75 -0.51 -0.99 -0.36 -1.63
[97] -0.98 0.61 1.01 0.55
# Note that anonymous functions aren't being called, but being passed.
> function() {print('hello #rstats')}()
function() {print('hello #rstats')}()
> a = function() {print('hello #rstats')}
> a
function() {print('hello #rstats')}
> a()
[1] "hello #rstats"
(对于那些关注#rstats的人,我也在那里发布了这个。)
请记住,使用apply,sapply,lapply,tapply和do.call!充分利用R的矢量化。你永远不应该走到一堆R代码,看看:
N = 10000
l = numeric()
for (i in seq(1:N)) {
sim <- rnorm(1, 0, 1)
l <- rbind(l, sim)
}
不仅没有矢量化,而且R中的数组结构也没有像Python中那样增长(当空间耗尽时,IIRC的大小加倍)。因此,每个rbind步骤必须首先增长到足以接受来自rbind()的结果,然后复制所有先前的内容。为了好玩,请在R中尝试上面的内容。注意它需要多长时间(您甚至不需要Rprof或任何计时功能)。然后尝试
N=10000
l <- rnorm(N, 0, 1)
以下优于第一个版本:
N = 10000
l = numeric(N)
for (i in seq(1:N)) {
sim <- rnorm(1, 0, 1)
l[i] <- sim
}
答案 16 :(得分:11)
根据Dirk的建议,我发布的是单个例子。我希望他们不是太“可爱”[聪明,但我不在乎]或对这些观众微不足道。
线性模型是R的基础。当自变量的数量很高时,有两个选择。第一个是它使用lm.fit(),它接收设计矩阵x和响应y作为参数,类似于Matlab。这种方法的缺点是返回值是一个对象列表(拟合系数,残差等),而不是类“lm”的对象,可以很好地总结,用于预测,逐步选择等。方法是创建一个公式:
> A
X1 X2 X3 X4 y
1 0.96852363 0.33827107 0.261332257 0.62817021 1.6425326
2 0.08012755 0.69159828 0.087994158 0.93780481 0.9801304
3 0.10167545 0.38119304 0.865209832 0.16501662 0.4830873
4 0.06699458 0.41756415 0.258071616 0.34027775 0.7508766
...
> (f=paste("y ~",paste(names(A)[1:4],collapse=" + ")))
[1] "y ~ X1 + X2 + X3 + X4"
> lm(formula(f),data=A)
Call:
lm(formula = formula(f), data = A)
Coefficients:
(Intercept) X1 X2 X3 X4
0.78236 0.95406 -0.06738 -0.43686 -0.06644
答案 17 :(得分:10)
您可以指定从if-else块返回的值。
而不是,例如
condition <- runif(1) > 0.5
if(condition) x <- 1 else x <- 2
你可以做到
x <- if(condition) 1 else 2
这究竟是如何运作的。但
答案 18 :(得分:10)
作为R的总菜鸟和统计数据的新手,我喜欢unclass()
将数据框的所有元素打印为普通列表。
一次性查看完整的数据集非常方便快速查看任何潜在问题。
答案 19 :(得分:9)
CrossTable()
包的 gmodels
可以轻松访问SAS和SPSS风格的交叉表,以及常用的测试(Chisq,McNemar等)。基本上,它是xtabs()
,具有奇特的输出和一些额外的测试 - 但它确实使得与异教徒的共享输出更容易。
答案 20 :(得分:7)
明确system()
。
能够从R环境内部访问所有unix工具(至少在Linux / MacOSX下),在我的日常工作流程中迅速变得非常宝贵。
答案 21 :(得分:6)
虽然这个问题已经持续了一段时间,但我最近在SAS and R blog上发现了使用命令cut
的一个很棒的技巧。该命令用于将数据划分为类别,我将使用虹膜数据集作为示例,并将其划分为10个类别:
> irisSL <- iris$Sepal.Length
> str(irisSL)
num [1:150] 5.1 4.9 4.7 4.6 5 5.4 4.6 5 4.4 4.9 ...
> cut(irisSL, 10)
[1] (5.02,5.38] (4.66,5.02] (4.66,5.02] (4.3,4.66] (4.66,5.02] (5.38,5.74] (4.3,4.66] (4.66,5.02] (4.3,4.66] (4.66,5.02]
[11] (5.38,5.74] (4.66,5.02] (4.66,5.02] (4.3,4.66] (5.74,6.1] (5.38,5.74] (5.38,5.74] (5.02,5.38] (5.38,5.74] (5.02,5.38]
[21] (5.38,5.74] (5.02,5.38] (4.3,4.66] (5.02,5.38] (4.66,5.02] (4.66,5.02] (4.66,5.02] (5.02,5.38] (5.02,5.38] (4.66,5.02]
[31] (4.66,5.02] (5.38,5.74] (5.02,5.38] (5.38,5.74] (4.66,5.02] (4.66,5.02] (5.38,5.74] (4.66,5.02] (4.3,4.66] (5.02,5.38]
[41] (4.66,5.02] (4.3,4.66] (4.3,4.66] (4.66,5.02] (5.02,5.38] (4.66,5.02] (5.02,5.38] (4.3,4.66] (5.02,5.38] (4.66,5.02]
[51] (6.82,7.18] (6.1,6.46] (6.82,7.18] (5.38,5.74] (6.46,6.82] (5.38,5.74] (6.1,6.46] (4.66,5.02] (6.46,6.82] (5.02,5.38]
[61] (4.66,5.02] (5.74,6.1] (5.74,6.1] (5.74,6.1] (5.38,5.74] (6.46,6.82] (5.38,5.74] (5.74,6.1] (6.1,6.46] (5.38,5.74]
[71] (5.74,6.1] (5.74,6.1] (6.1,6.46] (5.74,6.1] (6.1,6.46] (6.46,6.82] (6.46,6.82] (6.46,6.82] (5.74,6.1] (5.38,5.74]
[81] (5.38,5.74] (5.38,5.74] (5.74,6.1] (5.74,6.1] (5.38,5.74] (5.74,6.1] (6.46,6.82] (6.1,6.46] (5.38,5.74] (5.38,5.74]
[91] (5.38,5.74] (5.74,6.1] (5.74,6.1] (4.66,5.02] (5.38,5.74] (5.38,5.74] (5.38,5.74] (6.1,6.46] (5.02,5.38] (5.38,5.74]
[101] (6.1,6.46] (5.74,6.1] (6.82,7.18] (6.1,6.46] (6.46,6.82] (7.54,7.9] (4.66,5.02] (7.18,7.54] (6.46,6.82] (7.18,7.54]
[111] (6.46,6.82] (6.1,6.46] (6.46,6.82] (5.38,5.74] (5.74,6.1] (6.1,6.46] (6.46,6.82] (7.54,7.9] (7.54,7.9] (5.74,6.1]
[121] (6.82,7.18] (5.38,5.74] (7.54,7.9] (6.1,6.46] (6.46,6.82] (7.18,7.54] (6.1,6.46] (5.74,6.1] (6.1,6.46] (7.18,7.54]
[131] (7.18,7.54] (7.54,7.9] (6.1,6.46] (6.1,6.46] (5.74,6.1] (7.54,7.9] (6.1,6.46] (6.1,6.46] (5.74,6.1] (6.82,7.18]
[141] (6.46,6.82] (6.82,7.18] (5.74,6.1] (6.46,6.82] (6.46,6.82] (6.46,6.82] (6.1,6.46] (6.46,6.82] (6.1,6.46] (5.74,6.1]
10 Levels: (4.3,4.66] (4.66,5.02] (5.02,5.38] (5.38,5.74] (5.74,6.1] (6.1,6.46] (6.46,6.82] (6.82,7.18] ... (7.54,7.9]
答案 22 :(得分:6)
将因子转换为数字是一个烦人的解决方法。 (与其他数据类型相似)
old.var <- as.numeric(levels(old.var))[as.numeric(old.var)]
答案 23 :(得分:5)
set.seed()
设置随机数生成器状态。
例如:
> set.seed(123)
> rnorm(1)
[1] -0.5604756
> rnorm(1)
[1] -0.2301775
> set.seed(123)
> rnorm(1)
[1] -0.5604756
答案 24 :(得分:5)
对于那些写R从R调用的人来说:.Internal(inspect(...))
很方便。例如:
> .Internal(inspect(quote(a+2)))
@867dc28 06 LANGSXP g0c0 []
@8436998 01 SYMSXP g1c0 [MARK,gp=0x4000] "+"
@85768b0 01 SYMSXP g1c0 [MARK,NAM(2)] "a"
@8d7bf48 14 REALSXP g0c1 [] (len=1, tl=0) 2
答案 25 :(得分:5)
使用eval()
和parse()
时,我最喜欢的一个(如果不是非常不正确的技巧)。这个例子可能说明了它是如何有用的
NY.Capital <- 'Albany'
state <- 'NY'
parameter <- 'Capital'
eval(parse(text=paste(state, parameter, sep='.')))
[1] "Albany"
这种情况经常发生,使用eval()
和parse()
可以帮助解决这个问题。当然,我欢迎任何关于编写此代码的替代方法的反馈。
答案 26 :(得分:5)
另一招。某些软件包(如glmnet,仅)将设计矩阵和响应变量作为输入。如果想要使特征之间的所有交互适合模型,则她不能使用公式“y~. ^ 2”。使用expand.grid()
允许我们利用R的强大数组索引和向量运算。
interArray=function(X){
n=ncol(X)
ind=expand.grid(1:n,1:n)
return(X[,ind[,1]]*X[,ind[,2]])
}
> X
X1 X2
1 0.96852363 0.33827107
2 0.08012755 0.69159828
3 0.10167545 0.38119304
4 0.06699458 0.41756415
5 0.08187816 0.09805104
> interArray(X)
X1 X2 X1.1 X2.1
1 0.938038022 0.327623524 0.327623524 0.114427316
2 0.006420424 0.055416073 0.055416073 0.478308177
3 0.010337897 0.038757974 0.038757974 0.145308137
4 0.004488274 0.027974536 0.027974536 0.174359821
5 0.006704033 0.008028239 0.008028239 0.009614007
答案 27 :(得分:4)
d ='〜/ R Code / Library /'
files = list.files(d,'。r $')
for(文件中的f){ if(!(f =='mysource.r')){ 打印(粘贴( '采购',f))的 源(膏(d,F,九月= '')) } }
我使用上面的代码在启动时使用我在与R的交互式会话中使用的各种实用程序来获取目录中的所有文件。我相信有更好的方法,但我发现它对我的工作很有用。执行此操作的行如下。
source(“〜/ R Code / Library / mysource.r”)
答案 28 :(得分:3)
我提到这个,因为在SO上明显缺乏使用它的例子。
新的(ish)aggregate.formula语法使它比旧的通用聚合更灵活,更有用。它保留了聚合变量的名称,比列表语法更紧凑,并且它允许您同时执行多个变量,包括公式任一侧的点表示法。
使用
newdf <- aggregate( cbind(rt, acc) ~ x + y + subj, olddf, mean )
而不是......
newdf <- with( olddf, aggregate( rt, list(x = x, y = y, subj = subj), mean ))
names(newdf)[4] <- 'rt'
newdf$acc <- with( olddf,
aggregate( acc, list(x = x, y = y, subj = subj), mean ))[,4]
也许作为一个侧面注释......聚合的.data.frame示例也在聚合中。该功能做了许多人们不了解的事情。
答案 29 :(得分:3)
我以前曾经发过这个,但我用得太多了,我以为我会再发一次。它只是一个函数来返回data.frame的名称和位置号。它没什么特别可以确定的,但是我几乎没有在没有多次使用它的情况下通过会话。
##creates an object from a data.frame listing the column names and location
namesind =功能(DF){
temp1=names(df)
temp2=seq(1,length(temp1))
temp3=data.frame(temp1,temp2)
names(temp3)=c("VAR","COL")
return(temp3)
rm(temp1,temp2,temp3)
}
ni&lt; - namesind
答案 30 :(得分:3)
对数据框中的多个变量执行操作。这是从subset.data.frame中窃取的。
get.vars<-function(vars,data){
nl <- as.list(1L:ncol(data))
names(nl) <- names(data)
vars <- eval(substitute(vars), nl, parent.frame())
data[,vars]
#do stuff here
}
get.vars(c(cyl:hwy,class),mpg)
答案 31 :(得分:2)
作为最近的一个瘾君子,我喜欢?function_name并且一直使用它
-k
答案 32 :(得分:1)
似乎我无法评论(也许这与这个“声誉”业务有关)
无论如何,还要继续上面的RGoogleDocs提示:
ps <-readline(prompt="get the password in ")
这不适用于我喜欢用于R的Emacs,当然还有ESS。
在Linux上,你可以使用zenity从用户输入中获取密码,并将其设置为隐藏输入,所以作为额外的好处,你的密码在屏幕上不是明文:
mypass <- system("zenity --entry --hide-text",intern=TRUE)
答案 33 :(得分:0)
我喜欢这种语言的表现力,例如:选择:
df[df$col > something, c('col2', 'col3')]
tapply:
tapply(df$col_value, df$col_factor, function)
等