2014-09-18 62 views
2

我想写一点代码,它会根据开始日期获取数据框的一部分,每个开始日期对于每个用户都是不同的。在R中设置基于变量开始日期的数据

假设我有以下data.frames(在现实中我的数据集是幅度大几个数量级,但是这将足以作为样本集)

DF1:

> df 
     name start.date 
1 Allison 2013-03-16 
2 Andrew 2013-03-16 
3  Carl 2013-03-16 
4  Dora 2013-03-17 
5 Hilary 2013-03-17 
6 Louis 2013-03-18 
7  Mary 2013-03-19 
8 Mickey 2013-03-20 

而且DF2:

> df2 
     names X03.16.2013 X03.17.2013 X03.18.2013 X03.19.2013 
2001 Allison   5   5   0   0 
2002 Andrew   2   0   0   0 
2003 Carl   10   8   11   10 
2004 Dora   0   4   0   0 
2005 Hilary   0   3   5   0 
2006 Louis   0   0   8   3 
2007 Mary   0   0   0   7 
2008 Mickey   0   0   0   0 

我合并这两个数据帧到一个名为TMP:

>tmp 

    name start.date   X03.16.2013 X03.17.2013 X03.18.2013 X03.19.2013 
    1 Allison 2013-03-16   5   5   0   0 
    2 Andrew 2013-03-16   2   0   0   0 
    3  Carl 2013-03-16   10   8   11   10 
    4  Dora 2013-03-17   0   4   0   0 
    5 Hilary 2013-03-17   0   3   5   0 
    6 Louis 2013-03-18   0   0   8   3 
    7  Mary 2013-03-19   0   0   0   7 
    8 Mickey 2013-03-20   0   0   0   0 

我也有DF2的列名的列表转换为日期:

>dts 

[1] "2014-03-16" "2014-03-17" "2014-03-18" "2014-03-19" 

我认为解决这个问题的方法是改变所有在DF2零个条目每个用户的开始日期之前发生NA使用以下嵌套循环:

for (i in 1:dim(tmp)[1]){ 
    for (j in 1:length(dts)){ 
    for (z in 4:dim(tmp)[2]){ 
    if (dts[j]< tmp$Date.of.Sign.Up[i]){ 
     tmp[i,z]<-NA 
    } else {tmp[i,z]<-tmp[i,z]} 
    } 
} 
} 

该循环的问题是1.它将无限运行,并且2.不起作用。它将tmp中的所有值从tmp [,3:end]更改为零,无论开始日期如何。理想情况下,我会结束这样的事情:

 name start.date   X03.16.2013 X03.17.2013 X03.18.2013 X03.19.2013 
    Allison 2013-03-16   5   5   0   0 
    Andrew 2013-03-16   2   0   0   0 
    Carl 2013-03-16   10   8   11   10 
    Dora 2013-03-17   NA   4   0   0 
    Hilary 2013-03-17   NA   3   5   0 
    Louis 2013-03-18   NA   NA   8   3 
    Mary 2013-03-19   NA   NA   NA   7 
    Mickey 2013-03-20   NA   NA   NA   NA 

有什么建议吗?先谢谢你!

回答

0

您可能重塑“TMP”长格式,前者头转换成日期,他们开始日期进行比较,当“标题日期”后的开始日期发生插入NA

library(reshape2) 

# melt data from wide to long format 
df3 <- melt(tmp, id.vars = c("name", "start.date")) 

# convert 'variable' to class Date 
df3$variable <- as.Date(df3$variable, format = "X%m.%d.%Y") 

# compare start dates with 'variable dates' and insert NA 
df3$value[df3$start.date > df3$variable] <- NA 

# reshape back to wide 
dcast(df3, name + start.date ~ variable) 

#  name start.date 2013-03-16 2013-03-17 2013-03-18 2013-03-19 
# 1 Allison 2013-03-16   5   5   0   0 
# 2 Andrew 2013-03-16   2   0   0   0 
# 3 Carl 2013-03-16   10   8   11   10 
# 4 Dora 2013-03-17   NA   4   0   0 
# 5 Hilary 2013-03-17   NA   3   5   0 
# 6 Louis 2013-03-18   NA   NA   8   3 
# 7 Mary 2013-03-19   NA   NA   NA   7 
# 8 Mickey 2013-03-20   NA   NA   NA   NA 

另一个可能我们遍历在 'TMP' 的 '日期列名':

dates <- names(tmp)[-c(1, 2)] 

tmp[ , -c(1, 2)] <- sapply(dates, function(x){ 
    date <- as.Date(x, format = "X%m.%d.%Y") 
    tmp[ , x][df2$start.date > date] <- NA 
    tmp[ , x] 
}) 

tmp 
#  name start.date X03.16.2013 X03.17.2013 X03.18.2013 X03.19.2013 
# 1 Allison 2013-03-16   5   5   0   0 
# 2 Andrew 2013-03-16   2   0   0   0 
# 3 Carl 2013-03-16   10   8   11   10 
# 4 Dora 2013-03-17   NA   4   0   0 
# 5 Hilary 2013-03-17   NA   3   5   0 
# 6 Louis 2013-03-18   NA   NA   8   3 
# 7 Mary 2013-03-19   NA   NA   NA   7 
# 8 Mickey 2013-03-20   NA   NA   NA   NA 
+0

当你写的语句'DF3 < - 融(DF2,id.vars = C( “名”, “start.date” )'你是不是要说'df3 < - melt(df,id.vars = c(“name”,“start.date”))' – Archimeow 2014-09-18 21:57:30

+0

对于第二种解决方案,我我没有得到任何新加入。我不知道你是否提到df2你打算说tmp。我使用了下面的代码两次,一次假设你打算在所有你说的df2的地方说tmp,一次是这样的:'dates < - names(tmp)[ - c(1,2,3)]' 'tmp [ (x,format =“X%m。%d。%Y”) tmp [,x ] [tmp $ Date.of.Sign.Up Archimeow 2014-09-18 22:40:26

+0

both times没有NAs被插入 – Archimeow 2014-09-18 22:40:55

相关问题