我正在使用lapply大量项目上的复杂函数,我想保存每个项目的输出(如果有的话)以及生成的任何警告/错误,以便我可以告诉哪个项目产生了哪个警告/错误.
我找到了一种方法来捕捉警告withCallingHandlers(在此描述).但是,我也需要捕获错误.我可以将它包装在一个tryCatch(如下面的代码中),但是有更好的方法吗?
catchToList <- function(expr) {
val <- NULL
myWarnings <- NULL
wHandler <- function(w) {
myWarnings <<- c(myWarnings, w$message)
invokeRestart("muffleWarning")
}
myError <- NULL
eHandler <- function(e) {
myError <<- e$message
NULL
}
val <- tryCatch(withCallingHandlers(expr, warning = wHandler), error = eHandler)
list(value = val, warnings = myWarnings, error=myError)
}
Run Code Online (Sandbox Code Playgroud)
此函数的示例输出是:
> catchToList({warning("warning 1");warning("warning 2");1})
$value
[1] 1
$warnings
[1] "warning 1" "warning 2"
$error
NULL
> catchToList({warning("my warning");stop("my error")})
$value …Run Code Online (Sandbox Code Playgroud) 是否可以从...中删除元素并将...传递给其他函数?我的前两次尝试失败了:
parent = function(...)
{
a = list(...)
str(a)
a$toRemove = NULL
str(a)
# attempt 1
child(a)
# attempt 2
child( ... = a )
}
child = function(...)
{
a = list( ... )
str(a)
}
parent( a = 1 , toRemove = 2 )
Run Code Online (Sandbox Code Playgroud)
编辑
抱歉混乱.我修了孩子().目的是让孩子列出......的内容
Edit2
这里有一个更真实的例子(但仍然相当简单,所以我们可以就此进行有用的对话).父通过递归调用.父需要知道递归调用的深度.父母以外的来电者不应该知道"深度",也不应该在调用parent()时设置它.Parent调用其他函数,在本例中为child().孩子需要值...显然,孩子不需要"深度",因为父母为自己的使用生成了它.
parent = function( ... )
{
depth = list(...)$depth
if ( is.null( depth ) )
{
depth = 1
}
print( depth )
# parent needs value of depth to …Run Code Online (Sandbox Code Playgroud) 我试图找到一个函数来置换向量的所有唯一排列,同时不计算相同元素类型的子集内的并置.例如:
dat <- c(1,0,3,4,1,0,0,3,0,4)
Run Code Online (Sandbox Code Playgroud)
具有
factorial(10)
> 3628800
Run Code Online (Sandbox Code Playgroud)
可能的排列,但仅限于 10!/(2!*2!*4!*2!)
factorial(10)/(factorial(2)*factorial(2)*factorial(2)*factorial(4))
> 18900
Run Code Online (Sandbox Code Playgroud)
忽略同一元素类型的子集内的并置时的唯一排列.
我可以通过使用unique()和permn()包中的函数来获得这个combinat
unique( permn(dat) )
Run Code Online (Sandbox Code Playgroud)
但这在计算上非常昂贵,因为它涉及枚举n!,这可能比我需要的排列多一个数量级.没有先计算,有没有办法做到这一点n!?
我经常指定公式参数来模拟拟合函数,lm或者lme将我需要的部分粘贴在一起,就像@DWin对这个问题的回答一样:理解lm和环境.
在实践中,这看起来像这样:
library(nlme)
set.seed(5)
ns <- 5; ni <- 5; N <- ns*ni
d <- data.frame(y=rnorm(N),
x1=rnorm(N),
x2=factor(rep(1:ni, each=ns)),
id=factor(rep(1:ns, ni)))
getm <- function(xs) {
f <- paste("y ~", paste(xs, collapse="+"))
lme(as.formula(f), random=~1|id, data=d, method="ML")
}
m1 <- getm("x1")
m2 <- getm(c("x1", "x2"))
Run Code Online (Sandbox Code Playgroud)
但是,lme从nlme包中,比较使用方式构造的两个模型anova不起作用,因为anova.lme查看保存的公式参数以确保模型适合相同的响应,并且保存的公式参数很简单as.formula(f).错误是:
> anova(m1, m2)
Error in inherits(object, "formula") : object 'f' not found
Run Code Online (Sandbox Code Playgroud)
这是anova命令应该做的(重新安装模型以使其工作):
> m1 <- lme(y~x1, random=~1|id, …Run Code Online (Sandbox Code Playgroud) 我试图用多个因变量和多个自变量做回归.基本上我House Prices在整个美国的县级,这是我的IV.然后我在县级(GDP,construction employment)有几个其他变量,这些变量构成我的因变量.我想知道是否有一种有效的方法可以同时完成所有这些回归.我想得到:
lm(IV1 ~ DV11 + DV21)
lm(IV2 ~ DV12 + DV22)
Run Code Online (Sandbox Code Playgroud)
我想为每个独立变量和每个因变量做这个.
编辑: OP添加了这些信息以回应我的回答,现在已删除,误解了这个问题.
我不认为我很好地解释了这个问题,我道歉.每个因变量都有2个与之关联的独立变量,这是唯一的.因此,如果我有500个因变量,我有500个唯一的自变量1和500个唯一的自变量2.
好的,我会再试一次,如果我再也不能解释自己,我可能会放弃(哈哈).我不知道你mtcars对R的意思是什么[这是关于Metrics的答案],所以让我这样试试吧.我将有3个数据向量,每个数据大约500行.我正在尝试从每行数据中构建回归.假设向量1是我的因变量(我试图预测的那个),向量2和3组成我的自变量.因此,第一个回归将包含每个向量的第1行值,第2个将包含每个向量的第2行值,依此类推.再次感谢大家.
我无法确定更新github上我的R软件包版本号的工作流程,以避免错误地命名为"中间"版本.这就是我现在所做的.
这个问题是,如果有人(比方说我)在我做了一些修复之后从github下载但是在我碰到版本之前,他们认为他们拥有的版本是1.0.0(因为这仍然是描述中的内容) )但它真的有1.0.0和1.0.1之间的东西.
这样的事情似乎在" 是否有可能使用git/github添加版本号 "的问题中进行讨论,其中R不是特定的,所以我不知道它是否在谈论同样的事情或者如何无论如何,这将为R实施.
还有一个问题是" 自动增加R软件包的版本 ",它有一个自动更新它的答案,虽然在评论中,我们看到Hadley"基本上不会出售自动增加版本的好处"(https:// github. com/hadley/devtools/issues/501).那里的代码也取决于Make所以不是跨平台的.
我有一个相当大的对象列表,我想并行应用一个复杂的函数,但我当前的方法使用了太多的内存.我认为引用类可能会有所帮助,但使用mcapply它们来修改它们似乎不起作用.
该函数修改了对象本身,因此我用新的对象覆盖原始对象.由于该对象是一个列表,我只修改了它的一小部分,我希望R的复制修改语义可以避免生成多个副本; 然而,在运行它时,似乎并不是我正在做的事情.这是我一直使用的基本R方法的一个小例子.它正确地将余额重置为零.
## make a list of accounts, each with a balance
## and a function to reset the balance
foo <- lapply(1:5, function(x) list(balance=x))
reset1 <- function(x) {x$balance <- 0; x}
foo[[4]]$balance
## 4 ## BEFORE reset
foo <- mclapply(foo, reset1)
foo[[4]]$balance
## 0 ## AFTER reset
Run Code Online (Sandbox Code Playgroud)
似乎使用引用类可能会有所帮助,因为它们是可变的,并且在使用lapply它时确实按照我的预期进行; 余额重置为零.
Account <- setRefClass("Account", fields=list(balance="numeric"),
methods=list(reset=function() {balance <<- 0}))
foo <- lapply(1:5, function(x) Account$new(balance=x))
foo[[4]]$balance
## 4
invisible(lapply(foo, function(x) x$reset()))
foo[[4]]$balance
## 0
Run Code Online (Sandbox Code Playgroud)
但是当我使用时mclapply,它没有正确重置.请注意,如果您使用的是Windows …
我的数据框如下所示
models cores time
1 4 1 0.000365
2 4 2 0.000259
3 4 3 0.000239
4 4 4 0.000220
5 8 1 0.000259
6 8 2 0.000249
7 8 3 0.000251
8 8 4 0.000258
Run Code Online (Sandbox Code Playgroud)
......等
我想将其转换为表格/矩阵,其中#models用于行标签,#cores用于列标签,时间用作数据条目
例如
1 2 3 4 5 6 7 8
1 time data
4 time data
Run Code Online (Sandbox Code Playgroud)
目前我正在使用for循环将其转换为此结构,但我想知道是否有更好的方法?
我真的只想做点什么
x <- as.integer(c(1,2,3))
Run Code Online (Sandbox Code Playgroud)
但因为c(1,2,3)存储为浮点向量,我担心我会遇到截断问题,比如
> as.integer(1.99999999999)
[1] 1
Run Code Online (Sandbox Code Playgroud)
我怎么知道我很安全?
给定一行,一列或一个单元格的矩阵,我需要在保持矩阵结构的同时重新排序行.我尝试添加,drop=F但它不起作用!我做了什么?
test = matrix(letters[1:5]) # is a matrix
test[5:1,,drop=F] # not a matrix
test2 = matrix(letters[1:5],nrow=1) # is a matrix
test2[1:1,,drop=F] # not a matrix
test3 = matrix(1) # is a matrix
test3[1:1,,drop=F] # not a matrix
Run Code Online (Sandbox Code Playgroud) r ×10
algorithm ×1
ellipsis ×1
github ×1
matrix ×1
permutation ×1
statistics ×1
subset ×1
try-catch ×1