在for循环中使用ifelse inside mutate时遇到错误

时间:2016-11-01 16:02:53

标签: r if-statement for-loop dplyr

我有244个数据框的列表,如下所示: 列表的名称为datas

datas[[1]]

year  sal
2000 10000
2000 15000
2005 10000
2005 9000
2005 12000
2010 15000
2010 12000
2010 20000
2013 25000
2013 15000
2015 20000

我想创建一个名为fix.sal的新列,将不同年份的不同值相乘。例如,我在同一行的sal上乘以2乘以2000.以同样的方式,sal值乘以的数字是2005年的1.8,2010年的1.5,2013年的1.2 ,2015年为1.所以结果应该是这样的:

Year  sal  fix.sal
2000 10000  20000
2000 15000  30000
2005 10000  18000
2005 9000   16200
2005 12000  21600
2010 15000  22500
2010 12000  18000
2010 20000  30000
2013 25000  30000
2013 15000  18000
2015 20000  20000

我成功地使用了ifelse mutate内容dplyr。{/ p>

library(dplyr)
datas[[1]]<-mutate(datas[[1]], fix.sal=
ifelse(datas[[1]]$Year==2000,datas[[1]]$sal*2,
ifelse(datas[[1]]$Year==2005,datas[[1]]$sal*1.8,
ifelse(datas[[1]]$Year==2010,datas[[1]]$sal*1.5,
ifelse(datas[[1]]$Year==2013,datas[[1]]$sal*1.2,
datas[[1]]$sal*1)))))

但我必须对列表datas中的244个数据帧执行此操作。

所以我尝试使用for循环这样做;

for(i in 1:244){
datas[[i]]<-mutate(datas[[i]], fix.sal=
    ifelse(datas[[i]]$Year==2000,datas[[i]]$sal*2,
    ifelse(datas[[i]]$Year==2005,datas[[i]]$sal*1.8,
    ifelse(datas[[i]]$Year==2010,datas[[i]]$sal*1.5,
    ifelse(datas[[i]]$Year==2013,datas[[i]]$sal*1.2,
    datas[[i]]$sal*1)))))
}

然后出现了错误;

Error: invalid subscript type 'integer'

我该如何解决这个问题??

任何评论都将不胜感激! :)

2 个答案:

答案 0 :(得分:3)

请不要强迫自己使用ifelse。相反,使用乘数创建一个向量,然后使用年份从向量中进行选择。矢量看起来像这样:

multiplier <-
  c("2005" = 1.2
    , "2006" = 1.05
    , "2007" = 0.9)

无论您的数据中的每年乘数是多少。然后,这里有一些样本数据(都是相同的,但这并不重要):

datas <-
  lapply(1:3, function(idx){
    data.frame(
      Year = 2005:2007
      , sal = c(10, 20, 30)
    )
  })

最后,我们可以使用lapply更有效地遍历列表。每次都使用Yearmultipliers向量中选择一个值(注意使用as.character,否则它会选择,例如,第2005个条目,而不是命名为&#34; 2005&#34;)。

lapply(datas, function(x){
  mutate(x, fix.sal = sal*multiplier[as.character(Year)])
})

返回:

[[1]]
  Year sal fix.sal
1 2005  10      12
2 2006  20      21
3 2007  30      27

[[2]]
  Year sal fix.sal
1 2005  10      12
2 2006  20      21
3 2007  30      27

[[3]]
  Year sal fix.sal
1 2005  10      12
2 2006  20      21
3 2007  30      27

对于更紧凑的代码,您可以使用:

lapply(datas, mutate, fix.sal = sal*multiplier[as.character(Year)])

但是这让我不太清楚发生了什么。

答案 1 :(得分:0)

这是一个使用ifelse和lapply的简单解决方案:

# Creating the list
df <- data.frame(year=c(rep(2000,2),rep(2005,3),rep(2010,3),rep(2013,2),2015),
                 sal=c(10000,15000,10000,9000,12000,15000,12000,20000,25000,15000,20000))

datas <- list(df,df)

# Applying the function with ifelse
lapply(datas,function(x){
  outp <- ifelse(df$year==2000,df$sal*2,
         ifelse(df$year==2005,df$sal*1.8,
                ifelse(df$year==2010,df$sal*1.5,
                       ifelse(df$year==2013,df$sal*1.2,df$sal*1))))  

  return(outp)
})

您将获得列表中每个df的结果。