Covariance Matrix Test
Purpose
The purpose of this script is to check the covariance matrix changes year on year.
> head(temp.ret) GMT Nifty100Ret GoldRet Liquid 2004-05-28 0.4835926 0.08272835 0.03473777 2004-05-31 0.4595340 0.06904175 0.03464168 2004-06-01 0.4435187 0.07295139 0.03460823 2004-06-02 0.4645871 0.06749355 0.03457400 2004-06-03 0.4196550 0.06678886 0.03453988 2004-06-04 0.4315804 0.04620938 0.03450656 |
Split the dataset in to 5 years
> x <- as.xts(temp.ret) > yr.2004 <- x["2004", ] > cov.2004 <- cov(yr.2004) > n1 <- dim(coredata(yr.2004))[1] > yr.2005 <- x["2005", ] > cov.2005 <- cov(yr.2005) > n2 <- dim(coredata(yr.2005))[1] > yr.2006 <- x["2006", ] > cov.2006 <- cov(yr.2006) > n3 <- dim(coredata(yr.2006))[1] > yr.2007 <- x["2007", ] > cov.2007 <- cov(yr.2007) > n4 <- dim(coredata(yr.2007))[1] > yr.2008 <- x["2008", ] > cov.2008 <- cov(yr.2008) > n5 <- dim(coredata(yr.2008))[1] > yr.2009 <- x["2009", ] > cov.2009 <- cov(yr.2009) > n6 <- dim(coredata(yr.2009))[1] > yr.2010 <- x["2010", ] > cov.2010 <- cov(yr.2010) > n7 <- dim(coredata(yr.2010))[1] > n <- n1 + n2 + n3 + n4 + n5 + n6 + n7 > cov.total <- (n1 * cov.2004 + n2 * cov.2005 + n3 * cov.2006 + + n4 * cov.2007 + n5 * cov.2008 + n6 * cov.2009 + n7 * cov.2010)/(n) > test.stat <- n * det(cov.total) - (n1 * det(cov.2004) + n2 * + det(cov.2005) + n3 * det(cov.2006) + n4 * det(cov.2007) + + n5 * det(cov.2008) + n6 * det(cov.2009) + n7 * det(cov.2010)) > k <- 7 > p <- 3 > dof <- 0.5 * (k - 1) * (p) * (p + 1)/2 > print(test.stat) [1] 7.976251e-06 > print(qchisq(0.95, dof)) [1] 28.8693 |
- This result goes against the intuition as the test stat is less than chisquare stat and hence the covariance matrices are pretty stable!!
Ok, now let me do one more thing. compare cov and mcd based cov
> mcd.cov <- assetsMeanCov(temp.ret, "MCD")$cov > vanilla.cov <- assetsMeanCov(temp.ret, "MCD")$cov > cov.total <- 0.5 * mcd.cov + 0.5 * vanilla.cov > n1 <- dim(temp.ret)[1] > n2 <- dim(temp.ret)[1] > n <- n1 + n2 > test.stat <- n * det(cov.total) - n1 * det(mcd.cov) - n2 * det(vanilla.cov) > k <- 2 > p <- 3 > dof <- 0.5 * (k - 1) * (p) * (p + 1)/2 > print(test.stat) [1] 0 > print(qchisq(0.95, dof)) [1] 7.814728 |
WOW! it says that mcd based or vanilla based cov is the same
Is there a bug ? Let me simulate and check
> library(mnormt) > x1 <- rmnorm(n = 1000, mean = c(0, 0, 0), varcov = matrix(c(1, + 0.4, 0.7, 0.4, 1, 0.1, 0.7, 0.1, 1), nrow = 3, ncol = 3)) > x2 <- rmnorm(n = 1000, mean = c(0, 0, 0), varcov = matrix(c(1, + 0.4, 0.7, 0.4, 1, 0.1, 0.7, -0.1, 1), nrow = 3, ncol = 3)) > n1 <- dim(x1)[1] > cov.x1 <- cov(x1) > n2 <- dim(x2)[1] > cov.x2 <- cov(x2) > n <- n1 + n2 > cov.total <- 0.5 * cov.x1 + 0.5 * cov.x2 > test.stat <- n * det(cov.total) - n1 * det(cov.x1) - n2 * det(cov.x2) > k <- 2 > p <- 3 > dof <- 0.5 * (k - 1) * (p) * (p + 1)/2 > print(test.stat) [1] 26.62547 > print(qchisq(0.95, dof)) [1] 7.814728 |
Test stat is in the rejection region and hence cov matrices are diff
Slight perturbation
> library(mnormt) > x1 <- rmnorm(n = 1000, mean = c(0, 0, 0), varcov = matrix(c(1, + 0.4, 0.7, 0.4, 1, 0.1, 0.7, 0.1, 1), nrow = 3, ncol = 3)) > x2 <- rmnorm(n = 1000, mean = c(0, 0, 0), varcov = matrix(c(1, + 0.4, 0.65, 0.4, 1, 0.1, 0.65, 0.1, 1), nrow = 3, ncol = 3)) > n1 <- dim(x1)[1] > cov.x1 <- cov(x1) > n2 <- dim(x2)[1] > cov.x2 <- cov(x2) > n <- n1 + n2 > cov.total <- 0.5 * cov.x1 + 0.5 * cov.x2 > test.stat <- n * det(cov.total) - n1 * det(cov.x1) - n2 * det(cov.x2) > k <- 2 > p <- 3 > dof <- 0.5 * (k - 1) * (p) * (p + 1)/2 > print(test.stat) [1] 3.532013 > print(qchisq(0.95, dof)) [1] 7.814728 |
See, for small changes , it does not differentiate the change in the cov matrices Obviously one needs to look at the power of this test to get a feel of typeii error
One last test .. Have the cov matrices changed between 2004 and 2010
> yr.2004 <- x["2004", ] > cov.2004 <- cov(yr.2004) > n1 <- dim(coredata(yr.2004))[1] > yr.2010 <- x["2010", ] > cov.2010 <- cov(yr.2010) > n7 <- dim(coredata(yr.2010))[1] > n <- n1 + n7 > cov.total <- (n1 * cov.2004 + n7 * cov.2010)/(n) > test.stat <- n * det(cov.total) - (n1 * det(cov.2004) + n7 * + det(cov.2010)) > k <- 2 > p <- 3 > dof <- 0.5 * (k - 1) * (p) * (p + 1)/2 > print(test.stat) [1] 4.040607e-09 > print(qchisq(0.95, dof)) [1] 7.814728 |
Cov matrices have not changed between 2004 and 2010
What if I take daily returns!!
> library(fPortfolio) > dim(workdata.xts) [1] 1883 2 > nifgold.ret <- cbind(log(coredata(workdata.xts[2:1883, 1])/coredata(workdata.xts[1:1882, + 1])), log(coredata(workdata.xts[2:1883, 2])/coredata(workdata.xts[1:1882, + 2]))) > yr.2004 <- nifgold.ret[1:300, ] > cov.2004 <- cov(yr.2004) > n1 <- dim(coredata(yr.2004))[1] > yr.2010 <- nifgold.ret[1500:1830, ] > cov.2010 <- cov(yr.2010) > n7 <- dim(coredata(yr.2010))[1] > n <- n1 + n7 > cov.total <- (n1 * cov.2004 + n7 * cov.2010)/(n) > test.stat <- n * det(cov.total) - (n1 * det(cov.2004) + n7 * + det(cov.2010)) > k <- 2 > p <- 3 > dof <- 0.5 * (k - 1) * (p) * (p + 1)/2 > print(test.stat) [1] -3.363418e-06 > print(qchisq(0.95, dof)) [1] 7.814728 |
Does it mean covs are stable ? Atleast this test says so!