在 foreach 中使用 glm 的问题
Problems with using glm in foreach
我正在尝试使用 foreach 循环使多个 glms 变得有趣。我遇到的问题是当我尝试指定权重时它说找不到对象。下面是重现我遇到的问题的代码。
library(foreach)
library(doParallel)
registerDoParallel(cores=4)
getDoParWorkers()
train_samples<-vector(mode="list", length=4)
for(i in 1:4){
train_samples[[i]]<-sample(nrow(mtcars),nrow(mtcars)*.8,replace=FALSE)
}
train_samples
d_data<-mtcars
#Add a weights column to illustrate the issue. The actual weights would vary.
d_data$weights = 1
#This results in an error: object 'd_data' not found
foreach(k=1:4) %dopar%{
model.fit<-glm(formula='hp~cyl+disp+mpg',
family=poisson,
data=d_data[train_samples[[k]],],
weights=d_data[train_samples[[k]],12])
}
#Removing the weights condition makes it run fine.
foreach(k=1:4) %dopar%{
model.fit<-glm(formula='hp~cyl+disp+mpg',
family=poisson,
data=d_data[train_samples[[k]],])
}
我已经在网上寻找解决这个问题的方法,但一直找不到任何东西。我想知道为什么这是一个问题以及如何解决它。提前致谢!
编辑 1:我在下面添加了一个额外的示例。
w1<-numeric(25)+1
#This has the same problem with object w1 not being found.
#Setting .export="w1" doesn't help either
foreach(k=1:4, .export="w1") %dopar%{
model.fit<-glm(formula='hp~cyl+disp+mpg',
family=poisson,
data=d_data[train_samples[[k]],],
weights=w1)
}
#However, manually defining a numeric vector for weights works
foreach(k=1:4) %dopar%{
model.fit<-glm(formula='hp~cyl+disp+mpg',
family=poisson,
data=d_data[train_samples[[k]],],
weights=numeric(25)+1)
}
编辑 2:版本信息。
Windows 10
RStudio 版本:1.0.136
R 版本:3.3.1
foreach 版本:1.4.3
doParallel 版本:1.0.10
我能够重现您的错误。我不确定它为什么会出现,但我想出了一个有效的解决方案。
如果您将 glm 函数从循环中取出并创建一个单独的函数,然后在循环中使用它,它就可以工作。
model <- function(k, input_data, samples){
samples <- samples[[k]]
input_data <- input_data[samples,]
weights <- input_data[samples, 12]
print(weights)
model.fit <- glm(formula = 'hp ~ cyl + disp + mpg',
family = poisson,
data = input_data,
weights = weights)
return(model.fit)
}
trial.data <- foreach(k = 1:4,
.errorhandling = 'pass') %dopar% {
model(k, d_data, train_samples)
}
print(trial.data)
此外,如果您使用 .errorhandling
,它会为您提供更多信息,这些信息有时很有用(在这种情况下不是,只是供参考)。
希望这对你有用。
晚了,但问题是 glm()
首先在数据环境中寻找权重,然后才是公式。当您使用 %dopar%
并行 运行 时,您提供的权重向量不会出现在这些环境中。引用全局环境允许代码 运行 正确:
foreach(k=1:4) %dopar% {
#Create a weight vector, saves on globalenv() references later
w=d_data[train_samples[[k]],12]
model.fit<-glm(formula='hp~cyl+disp+mpg',
family=poisson,
data=d_data[train_samples[[k]],],
#Instruct glm() to look in the global environment for weights
weights=globalenv()$w)
}
我正在尝试使用 foreach 循环使多个 glms 变得有趣。我遇到的问题是当我尝试指定权重时它说找不到对象。下面是重现我遇到的问题的代码。
library(foreach)
library(doParallel)
registerDoParallel(cores=4)
getDoParWorkers()
train_samples<-vector(mode="list", length=4)
for(i in 1:4){
train_samples[[i]]<-sample(nrow(mtcars),nrow(mtcars)*.8,replace=FALSE)
}
train_samples
d_data<-mtcars
#Add a weights column to illustrate the issue. The actual weights would vary.
d_data$weights = 1
#This results in an error: object 'd_data' not found
foreach(k=1:4) %dopar%{
model.fit<-glm(formula='hp~cyl+disp+mpg',
family=poisson,
data=d_data[train_samples[[k]],],
weights=d_data[train_samples[[k]],12])
}
#Removing the weights condition makes it run fine.
foreach(k=1:4) %dopar%{
model.fit<-glm(formula='hp~cyl+disp+mpg',
family=poisson,
data=d_data[train_samples[[k]],])
}
我已经在网上寻找解决这个问题的方法,但一直找不到任何东西。我想知道为什么这是一个问题以及如何解决它。提前致谢!
编辑 1:我在下面添加了一个额外的示例。
w1<-numeric(25)+1
#This has the same problem with object w1 not being found.
#Setting .export="w1" doesn't help either
foreach(k=1:4, .export="w1") %dopar%{
model.fit<-glm(formula='hp~cyl+disp+mpg',
family=poisson,
data=d_data[train_samples[[k]],],
weights=w1)
}
#However, manually defining a numeric vector for weights works
foreach(k=1:4) %dopar%{
model.fit<-glm(formula='hp~cyl+disp+mpg',
family=poisson,
data=d_data[train_samples[[k]],],
weights=numeric(25)+1)
}
编辑 2:版本信息。
Windows 10
RStudio 版本:1.0.136
R 版本:3.3.1
foreach 版本:1.4.3
doParallel 版本:1.0.10
我能够重现您的错误。我不确定它为什么会出现,但我想出了一个有效的解决方案。
如果您将 glm 函数从循环中取出并创建一个单独的函数,然后在循环中使用它,它就可以工作。
model <- function(k, input_data, samples){
samples <- samples[[k]]
input_data <- input_data[samples,]
weights <- input_data[samples, 12]
print(weights)
model.fit <- glm(formula = 'hp ~ cyl + disp + mpg',
family = poisson,
data = input_data,
weights = weights)
return(model.fit)
}
trial.data <- foreach(k = 1:4,
.errorhandling = 'pass') %dopar% {
model(k, d_data, train_samples)
}
print(trial.data)
此外,如果您使用 .errorhandling
,它会为您提供更多信息,这些信息有时很有用(在这种情况下不是,只是供参考)。
希望这对你有用。
晚了,但问题是 glm()
首先在数据环境中寻找权重,然后才是公式。当您使用 %dopar%
并行 运行 时,您提供的权重向量不会出现在这些环境中。引用全局环境允许代码 运行 正确:
foreach(k=1:4) %dopar% {
#Create a weight vector, saves on globalenv() references later
w=d_data[train_samples[[k]],12]
model.fit<-glm(formula='hp~cyl+disp+mpg',
family=poisson,
data=d_data[train_samples[[k]],],
#Instruct glm() to look in the global environment for weights
weights=globalenv()$w)
}