2016-07-29 47 views
0

这是我的第一篇文章,所以如果我没有足够具体,我会道歉。计算从一个数据框中的列到按照多个行的顺序中的每个月的月数

我有一个月的序列和一个约100行的数据框,每个都有一个唯一的标识符。每个标识符都与启动日期相关联。我正在计算序列中每月每个唯一标识符启动后的月数。我已经尝试写一个for循环来完成这个。

下例:

# Build Example Data Frame # 
x_example <- c("A","B","C","D","E") 
y_example <- c("2013-10","2013-10","2014-04","2015-06","2014-01") 
x_name <- "ID" 
y_name <- "StartUp" 
df_example <- data.frame(x_example,y_example) 
names(df_example) <- c(x_name,y_name) 

# Create Sequence of Months, Format to match Data Frame, Reverse for the For Loop # 
base.date <- as.Date(c("2015-11-1")) 
Months <- seq.Date(from = base.date , to = Sys.Date(), by = "month") 
Months.1 <- format(Months, "%Y-%m") 
Months.2 <- rev(Months.1) 

# Create For Loop # 
require(zoo) 
for(i in seq_along(Months.2)) 
{ 
    for(j in 1:length(summary(as.factor(df_example$ID), maxsum = 100000))) 
    { 
    Active.Months <- 12 * as.numeric((as.yearmon(Months.2 - i) - as.yearmon(df_example$StartUp))) 
    } 
} 

背后的for循环是在Months.2序列中的每个记录,会有的月数的计算,以该记录(年月日)从想法每个唯一标识符的启动月份。然而,这已被踢回错误:

Error in Months.2 - i : non-numeric argument to binary operator

我不知道该解决方案是什么,或者,如果我使用的for循环正常了这一点。

在此先感谢您解决此问题的任何帮助!

编辑:这是我希望我的预期的结果将是(这仅仅是一个样品有序列中个月以上):

ID Start Up Month 2015-11 2015-12 2015-12 2016-02 2016-03 
1 A  2013-10  25  26  27  28  29 
2 B  2013-10  25  26  27  28  29 
3 C  2014-04  19  20  21  22  23 
4 D  2015-06  5  6  7  8  9 
5 E  2014-01  22  23  24  25  26 
+0

你能发表一个你期待什么输出的例子,以便人们更容易正确回答你的问题吗? –

+1

我加了预期的输出,对不起! – DW1

回答

1

一种方式来做到这一点是首先使用as.yearmonzoo包转换日期。然后,只需我们遍历个月,从df_example的那些减,

library(zoo) 

df_example$StartUp <- as.Date(as.yearmon(df_example$StartUp)) 
Months.2 <- as.Date(as.yearmon(Months.2)) 

df <- as.data.frame(sapply(Months.2, function(i) 
        round(abs(difftime(df_example$StartUp, i, units = 'days')/30)))) 
names(df) <- Months.2 
cbind(df_example, df) 

# ID StartUp 2016-07 2016-06 2016-05 2016-04 2016-03 2016-02 2016-01 2015-12 2015-11 
#1 A 2013-10  33  32  31  30  29  28  27  26  25 
#2 B 2013-10  33  32  31  30  29  28  27  26  25 
#3 C 2014-04  27  26  25  24  23  22  21  20  19 
#4 D 2015-06  13  12  11  10  9  8  7  6  5 
#5 E 2014-01  30  29  28  27  26  25  24  23  22 
+0

这太好了,非常感谢! – DW1

0
x_example <- c("A","B","C","D","E") 
y_example <- c("2013-10","2013-10","2014-04","2015-06","2014-01") 
y_example <- paste(y_example,"-01",sep = "") 

# past on the "-01" because I want the later function to work. 

x_name <- "ID" 
y_name <- "StartUp" 
df_example <- data.frame(x_example,y_example) 
names(df_example) <- c(x_name,y_name) 


base.date <- as.Date(c("2015-11-01")) 
Months <- seq.Date(from = base.date , to = Sys.Date(), by = "month") 
Months.1 <- format(Months, "%Y-%m-%d") 
Months.2 <- rev(Months.1) 

monnb <- function(d) { lt <- as.POSIXlt(as.Date(d, origin="1900-01-01")); lt$year*12 + lt$mon } 
mondf <- function(d1, d2) {monnb(d2) - monnb(d1)} 

NumofMonths <- abs(mondf(df_example[,2],Sys.Date())) 

n = max(NumofMonths) 

# sequence along the number of months and get the month count. 

monthcount <- (t(sapply(NumofMonths, function(x) pmax(seq((x-n+1),x, +1), 0)))) 
monthcount <- data.frame(monthcount[,-(1:24)]) 
names(monthcount) <- Months.1 

finalDataFrame <- cbind.data.frame(df_example,monthcount) 

这里是被期望的输出,你表示,你的最终数据帧:

ID StartUp 2015-11-01 2015-12-01 2016-01-01 2016-02-01 2016-03-01 2016-04-01 2016-05-01 2016-06-01 2016-07-01 
1 A 2013-10-01   25   26   27   28   29   30   31   32   33 
2 B 2013-10-01   25   26   27   28   29   30   31   32   33 
3 C 2014-04-01   19   20   21   22   23   24   25   26   27 
4 D 2015-06-01   5   6   7   8   9   10   11   12   13 
5 E 2014-01-01   22   23   24   25   26   27   28   29   30 

的总体思路是我们计算月数并使用序列函数创建月数的计数器,直到获得当前月份。

+0

感谢您将它放在一起,这真的有帮助! – DW1

+0

@ DW1如果你认为这是最好的答案,那么请点击“检查”标记 –