Here is one possible approach:
melt
the data, as you suggested...
...and, use colsplit
to split up the "variable" into the "Mon" and "Year" columns.
library(reshape2)
ddt.m <- melt(df, id = c("x", "y"))
ddt.m <- cbind(ddt.m, colsplit(ddt.m$variable, "\\.", c("Mon", "Year")))
Use factor
and levels
to get your seasons
(which I've left in the "Mon" column. Oops.)
ddt.m$Mon <- factor(ddt.m$Mon)
levels(ddt.m$Mon) <- list(Winter = month.abb[c(12, 1, 2)],
Spring = month.abb[c(3:5)],
Summer = month.abb[c(6:8)],
Autumn = month.abb[c(9:11)])
head(ddt.m)
# x y variable value Mon Year
# 1 1214842 991964.4 Jan.2009 -1.332933 Winter 2009
# 2 1220442 991964.4 Jan.2009 -1.345808 Winter 2009
# 3 1226042 991964.4 Jan.2009 -1.314435 Winter 2009
# 4 1231642 991964.4 Jan.2009 -1.236600 Winter 2009
# 5 1237242 991964.4 Jan.2009 -1.261989 Winter 2009
# 6 1242842 991964.4 Jan.2009 -1.306614 Winter 2009
Use dcast
to aggregate the data
dfSeasonMean <- dcast(ddt.m, x + y ~ Mon + Year,
value.var="value", fun.aggregate=mean)
head(dfSeasonMean)
# x y Winter_2009 Winter_2010 Spring_2009 Spring_2010 Summer_2009
# 1 1214842 991964.4 -1.439480 -1.006512 -0.02509008 0.2823048 1.392440
# 2 1220442 964154.4 -1.457407 -1.039266 -0.04337596 0.2315217 1.422541
# 3 1220442 973424.4 -1.456991 -1.035115 -0.04117584 0.2423561 1.414473
# 4 1220442 982694.4 -1.456479 -1.029627 -0.03799926 0.2544062 1.405813
# 5 1220442 991964.4 -1.456234 -1.027081 -0.03815661 0.2610397 1.400743
# 6 1226042 945614.4 -1.463465 -1.031665 -0.04288670 0.2236609 1.434002
# Summer_2010 Autumn_2009 Autumn_2010
# 1 1.256840 0.06469363 -0.03823892
# 2 1.263593 0.04521096 -0.04485553
# 3 1.258328 0.04860321 -0.04477636
# 4 1.252779 0.05337575 -0.04729598
# 5 1.247251 0.05742809 -0.05152524
# 6 1.272742 0.04692731 -0.04915314