在R中计算时间序列数据中每年各日期均值及处理闰年方法
计算年际同日平均温度及闰年处理方案
一、提取月日标识并计算同日平均
首先从你的日均温数据框m_tc中提取月-日格式的标识,用来按“每年同一天”分组:
# 给m_tc添加月-日列,格式如"01-01" m_tc$month_day <- format(m_tc$dia, "%m-%d") # 按month_day分组,计算同日平均温度 daily_avg <- aggregate(tc_h ~ month_day, m_tc, mean)
此时daily_avg会有366行(包含闰年的2月29日数据),接下来处理闰年问题得到365行结果。
二、闰年(2月29日)的三种处理方式
2007-2021年间的闰年为2008、2012、2016、2020,共4个2月29日,常见处理方式如下:
1. 直接剔除2月29日数据
如果你的分析不需要考虑2月29日,直接过滤该行即可得到365行结果:
# 移除2月29日的记录 daily_avg_365 <- daily_avg[daily_avg$month_day != "02-29", ]
2. 将2月29日数据合并到2月28日
若希望保留闰年数据的影响,可将2月29日的平均温度与2月28日的合并计算:
# 提取2月29日的平均温度 leap_temp <- daily_avg[daily_avg$month_day == "02-29", "tc_h"] # 找到2月28日的行索引 feb28_row <- which(daily_avg$month_day == "02-28") # 重新计算2月28日的平均(包含闰年2月29日的数据) daily_avg[feb28_row, "tc_h"] <- mean(c(daily_avg[feb28_row, "tc_h"], leap_temp)) # 移除2月29日记录 daily_avg_365 <- daily_avg[daily_avg$month_day != "02-29", ]
3. 插值估算平年等效值(进阶)
如果需要更精细的处理,可通过2月28日和3月1日的平均温度插值估算2月29日的“平年值”,再将其合并到序列中(但一般场景下前两种方法已足够):
# 提取2月28日、3月1日的平均温度 feb28_temp <- daily_avg[daily_avg$month_day == "02-28", "tc_h"] mar1_temp <- daily_avg[daily_avg$month_day == "03-01", "tc_h"] # 插值得到2月29日的估算值 leap_est <- (feb28_temp + mar1_temp) / 2 # 替换原2月29日的值,再剔除该行 daily_avg[daily_avg$month_day == "02-29", "tc_h"] <- leap_est daily_avg_365 <- daily_avg[daily_avg$month_day != "02-29", ]
三、用dplyr实现更简洁的流程
如果你习惯用tidyverse工具,代码会更简洁:
library(dplyr) daily_avg_365 <- m_tc %>% mutate(month_day = format(dia, "%m-%d")) %>% # 将所有2月29日映射为2月28日 mutate(month_day = if_else(month_day == "02-29", "02-28", month_day)) %>% group_by(month_day) %>% summarise(avg_tc = mean(tc_h)) %>% ungroup()
内容的提问来源于stack exchange,提问作者Théo Arueira
相关产品推荐
相关产品推荐

