2014-09-18 2 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 :

>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 
     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에이 두 데이터 프레임 병합 나는 각 사용자의 시작 날짜 이전에 발생 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]에서 0으로 변경합니다. 이상적으로 나는 이런 식으로 끝날 것입니다 :

 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 

또 다른를 `df2, id.vars = c ("name", "start.date") 문을 쓸 때 'tmp'의 'date column names'를 반복 할 수있는 가능성 :

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 <- melt (df, id.vars = c ("name", "start.date"))' – Archimeow

+0

두 번째 해결책으로, NAs가 들어갈 수 없어요. 당신이 df2를 추천했을 때 당신이 tmp를 말할 의도가 있는지 확실하지 않았습니다. 나는 다음과 같은 코드를 두 번 사용했다. 한 번은 dmp를 df2라고 말하면서 tmp라고 말하려는 의도로 한 번 사용되었다 :'dates <- names (tmp) [-c (1, 2,3)]' 'tmp [ -d (x, format = "X % m. % d. % Y") tmp [, x ] [tmp $ Date.of.Sign.Up <- NA tmp [, x]})' – Archimeow

+0

두 번 NO는 삽입되지 않았습니다. – Archimeow

관련 문제