r - 当某些日期为 NA 时,按日期合并 R 中的两个数据框
问题描述
我有两个数据框;
df.tweets <- data.frame(Date = c(as.Date("2020-12-26"), as.Date="2020-12-15", as.Date="2021-01-12"), Tweet = c("abs", "ksk", "sks"), Ticker = c("NFLX", "GOOGL", "FB"))
Date Tweet Ticker
1 2020-12-26 abs NFLX
2 2020-12-15 ksk GOOGL
3 2021-01-12 sks FB
df.finance <- data.frame(Date = c(as.Date("2020-12-25"), as.Date="2020-12-27", as.Date="2020-12-15", as.Date="2021-01-12"), AR = c("0.23", "0.34", "0.44", "0.91"), Ticker = c("NFLX", "NFLX", "GOOGL", "FB"))
Date AR Ticker
1 2020-12-25 0.23 NFLX
2 2020-12-27 0.34 NFLX
3 2020-12-15 0.44 GOOGL
4 2021-01-12 0.91 FB
我想将这两个数据框合并成这样的东西;
df.output <- data.frame(Date = c(as.Date("2020-12-27"), as.Date="2020-12-15", as.Date="2021-01-12"), Tweet = c("abs", "ksk", "sks"), Ticker = c("NFLX", "GOOGL", "FB"), AR = c("0.34", "0.44", "0.91"))
Date Tweet Ticker AR
1 2020-12-27 abs NFLX 0.34
2 2020-12-15 ksk GOOGL 0.44
3 2021-01-12 sks FB 0.91
最初使用此代码;
df.new_analysis <- merge(df.new, df.finance, by = c("Date", "Ticker"), all.x = TRUE)
但是,由于某些推文是在周末发布的,因此没有与日期相对应的股票数据。我找到了周六和周日的推文,并将日期更改为下周一(合并数据框之前)以查找下一个交易日。
df.tweets$weekday <- weekdays(df.tweets$Date)
df.tweets$Date <- as.Date(df.tweets$Date)
for (row in 1:nrow(df.tweets)){
if (df.tweets[row, 4] == "Saturday") { # 4 = Weekday column
df.tweets[row, 1] <- df.tweets[row, 1] + 2 # 1 = Date column
}
else if (df.tweets[row, 4] == "Sunday"){
df.tweets[row, 1] <- df.tweets[row, 1] + 1
}
}
但是,现在我遇到的问题是,有些交易日期是工作日(不是周末),但由于公共假期(例如复活节星期一),证券交易所休市。
有没有比在日列中添加天数直到没有 NA 更简单的方法来解决这个问题?例如,如果没有相应的日期,则合并数据框以在 df.finance 中查找第二天。
我并不关心数据列是推文日期还是AR(异常返回),只要AR来自下一个交易日而不是前一个交易日。
解决方案
One way using dplyr
:
library(dplyr)
df.tweets %>%
#Join the two dataframes
full_join(df.finance, by = 'Ticker') %>%
#Arrange the data by date
arrange(Ticker, Date.x) %>%
#Get the difference between the dates
mutate(diff = Date.y - Date.x) %>%
#For each ticker and date
group_by(Ticker, Date.x) %>%
#Select the first row where the
#difference is greater than equal to 0
slice(which.max(diff >= 0)) %>%
ungroup %>%
#Select and rename columns.
select(Date = Date.y, everything(), -diff, -Date.x)
# Date Tweet Ticker AR
# <date> <chr> <chr> <chr>
#1 2021-01-12 sks FB 0.91
#2 2020-12-15 ksk GOOGL 0.44
#3 2020-12-27 abs NFLX 0.34