【问题标题】:R Sorting Data Frame by DateR按日期对数据帧进行排序
【发布时间】:2012-06-26 18:35:03
【问题描述】:

我正在研究 R data.frame,它由股票每年的股息组成(我有 60 列股票和行中的常用日历)。支付股息时,我有这个数字,否则有一个NA

基本上,这是我的 Data.frame 的样子

           BARC LN      BARN SE  BAS GY  BATS LN 
1999-01-01      0.26       NA      NA
1999-01-02       NA       0.56     0.35     NA
1999-01-03       NA        NA      NA       NA
2000-01-04       NA        NA      0.40     NA
1999-01-05      0.23      0.28     NA       NA
2001-01-06       NA        NA      NA       NA
2001-01-07      0.85       NA     0.15      NA

我想获得每只股票每年支付的股息金额,以计算股息收益率并最终获得如下数据;

           BARC LN   BARN SE  BAS GY  BATS LN 
   1999       NA        NA      NA       NA
   2000       NA        NA      NA       NA
   2001       NA        NA      NA       NA

我该怎么做?

【问题讨论】:

  • 你试过什么?看起来你的日期是row.names?您可以使用dput 发布您的实际数据的子集。它会让你更容易给你一个正确的答案。
  • 这是我尝试过的,但它没有为我提供股票股息,因为我只有日期:years
  • 对不起,Div 是包含我所有数据的data.frame

标签: r dataframe time-series finance stockquotes


【解决方案1】:

因此,假设您的数据位于一个 data.frame 中,就像您在上面发布的那样,名为 div

div <- structure(list(barc.ln = c(0.26, NA, NA, NA, 0.23, NA, 0.85), 
    barn.se = c(NA, 0.56, NA, NA, 0.28, NA, NA), bas.gy = c(NA, 
    0.35, NA, 0.4, NA, NA, 0.15), bats.ln = c(NA, NA, NA, NA, 
    NA, NA, NA)), .Names = c("barc.ln", "barn.se", "bas.gy", 
"bats.ln"), row.names = c("1999-01-01", "1999-01-02", "1999-01-03", 
"2000-01-04", "1999-01-05", "2001-01-06", "2001-01-07"), class = "data.frame")

正如您所做的那样,您可以从row.names 中提取年份:

div$years <- as.POSIXlt(row.names(div))$year + 1900

plyrreshape2 包在这里运行良好,我认为使代码特别清晰。具体来说,我将使用melt 使数据变长,然后使用ddply 进行分组,并使用sum 进行分红:

library(plyr)
library(reshape2)
div.melt <- melt(div, id.vars='years')
div.sum <- ddply(div.melt, 
                 .(years, variable), 
                 summarise, 
                 dividend = sum(value, na.rm=TRUE))

> div.sum
 years variable dividend
1   1999  barc.ln     0.49
2   1999  barn.se     0.84
3   1999   bas.gy     0.35
4   1999  bats.ln     0.00
5   2000  barc.ln     0.00
6   2000  barn.se     0.00
7   2000   bas.gy     0.40
8   2000  bats.ln     0.00
9   2001  barc.ln     0.85
10  2001  barn.se     0.00
11  2001   bas.gy     0.15
12  2001  bats.ln     0.00
> 

然后您可以使用 reshape2 中的另一个名为 cast 的函数来“宽”格式化您的数据:

> dcast(div.sum, years ~ variable, value.var='dividend')
  years barc.ln barn.se bas.gy bats.ln
1  1999    0.49    0.84   0.35       0
2  2000    0.00    0.00   0.40       0
3  2001    0.85    0.00   0.15       0
> 

【讨论】:

  • 此功能不起作用:reduces.sum
  • @user1474263 如果您使用我提供的数据,它会起作用。如果您使用函数 dput 给我们您的代码的可复制副本,那么我可以提供进一步的帮助。该错误表明您正在尝试计算字符向量的总和,这当然是不可能的。但是如果没有看到您的一些可用格式的数据,我无法帮助调试。
【解决方案2】:

我认为使用 by() 可以很容易地做到这一点。这就是我的做法。我已将每个块以及每个块下方的说明放在一起。

dividends <- data.frame(barc_ln=c(0.26,NA,NA,NA,0.23,NA,0.85),
                        barn_se=c(NA,0.56,NA,NA,0.28,NA,NA),
                        bas_gy=c(NA,0.35,NA,0.40,NA,NA,0.15),
                        bats_ln=c(NA,NA,NA,NA,NA,NA,NA),
                        row.names=c("1999-01-01","1999-01-02","1999-01-03","2000-01-04","1999-01-05","2001-01-06","2001-01-07"))

这只是创建了您提供的原始数据框。

dividends[,"dates"] <- as.Date(row.names(dividends))
dividends <- dividends[order(dividends[,"dates"]),]
dividends[,"year"] <- format(dividends$dates,"%Y")

这将获取行名日期,然后将它们转换为数据框中的新列(“日期”)。然后,我们按日期排序数据框(不一定需要,但我发现它更直观)并使用格式提取年份(作为一个字符,请注意)。

div_output <- data.frame(row.names=unique(dividends$year))

接下来,我创建将接收数据的输出数据框。我对 year 变量使用 unique() 函数来获取唯一的年份向量。它们已经排序(排序数据框的一个优点)。

for(x in 1:4) {
    div_output[,x] <- by(dividends[,x],INDICES=dividends$year,FUN=sum,na.rm=TRUE)
}
names(div_output) <- names(dividends)[1:4]

使用一个简单的循环,我们只需遍历每一列并应用 by() 函数。变量是列,索引是年份,我们只使用 sum 函数。我在 na.rm=TRUE 上进行标记,以便您获得实际数据而不是 NA。

print(div_output)

     barc_ln barn_se bas_gy bats_ln
1999    0.49    0.84   0.35       0
2000    0.00    0.00   0.40       0
2001    0.85    0.00   0.15       0

这就是我得到的输出。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-12-09
    • 2022-01-08
    • 1970-01-01
    • 2022-01-08
    • 2016-07-26
    • 1970-01-01
    • 2012-07-20
    相关资源
    最近更新 更多