用已知的mu和cov矩阵进行组合优化

时间:2021-01-19 12:34:15

Would like to optimize a portfolio in fPortfolio ideally where the vector mu (returns) and the covariance matrix are already known (from some other algorithm which does the calculation). So, let's say I have the following:

想要在fPortfolio中优化一个组合,理想的情况是,已知向量mu(返回)和协方差矩阵(从其他算法中计算)。那么,假设我有下面的:

mu = c(0.05,0.1,0.075,0.06)
cov=    
0.02657429 0.01805751 0.02048764 0.02110555
0.01805751 0.03781108 0.03859943 0.02959261
0.02048764 0.03859943 0.04606304 0.03043146
0.02110555 0.02959261 0.03043146 0.03880064

Now, I would like to do

现在,我想这样做

efficientPortfolio(data, spec = portfolioSpec(), constraints = "LongOnly")

with returns and covariance as specfied above. How would that work?

返回和协方差如上所述。如何工作?

Regards Andreas

认为安德烈亚斯

3 个解决方案

#1


1  

You need to do something like this:

你需要这样做:

library(quadprog)

d = rep(0,4); #4 - no. of stocks
A = rbind(rep(1,4), #1st const. --- sum of weights should be 1
                mu, #2nd const. --- returns should be positive
                diag(4) #3rd const ---- all the weights are positive   
        );
b = c(1, 0, rep(0,4) );
solve.QP(cov, d, t(A), b, meq=1)

#2


1  

I am not an expert in the fPortfolio package. But it looks like you need to define your own fPFOLIODATA object. In fPortfolio this is done in the portfolioData() function. So a quick and dirty solution might be to write your own function that doesn't do the covariance estimation but takes as input your estimated mu and sigma. So here is my solution:

我不是fPortfolio的专家。但是看起来您需要定义自己的fPFOLIODATA对象。在fPortfolio中,这是在portfolioData()函数中完成的。所以一个快速而棘手的解决方案可能是写出你自己的函数它不做协方差估计,而是作为你的估计和的输入。这就是我的解:

myPortfolioData <- function(mu, sigma, data, spec){
    if (is(data, "fPFOLIODATA")) 
        return(data)
    stopifnot(class(data) == "timeSeries")
    data = sort(data)
    nAssets = NCOL(data)
    names = colnames(data)
    if (is.null(names)) 
        names = paste("A", 1:nAssets, sep = "")
    Cov = cov(data)
    rownames(Cov) <- colnames(Cov) <- names
    .data = list(series = data, nAssets = nAssets, names = names)
    .statistics <- list(mean = colMeans(data), Cov = Cov, estimator = 'other', mu = mu, Sigma = covar);
    .tailRisk = spec@model$tailRisk
    new("fPFOLIODATA", data = .data, statistics =.statistics, tailRisk = .tailRisk)
}

Let's test if it gives the same results:

让我们来测试它是否给出了相同的结果:

library(fPortfolio)

#This is how you would usually do it
defaultSpec <- portfolioSpec()
setTargetReturn(defaultSpec) <- 0.06
lppAssets <- 100*LPP2005.RET[, c("SBI", "SPI", "LMI", "MPI")]
lppData <- portfolioData(data = lppAssets, spec = defaultSpec)
port <- efficientPortfolio(lppData, defaultSpec, constraints = "LongOnly")

#Now I am creating my own mu and sigma 
#In this case exactly the same as the estimation above to see if the results match  
mu <- c(SBI=0.0000406634, SPI=0.0841754390, LMI=0.0055315332, MPI=0.0590515119)
sigma <- matrix(c(0.015899554, -0.01274142,  0.009803865, -0.01588837,-0.012741418,  0.58461212, -0.014074691,  0.41159843,0.009803865, -0.01407469,  0.014951108, -0.02332223,-0.015888368,  0.41159843, -0.023322233,  0.53503263), 4, 4, dimnames=list(names(mu), names(mu))) 
myLppData <- myPortfolioData(mu, sigma, lppAssets, defaultSpec)
myPort <- efficientPortfolio(myLppData, defaultSpec, constraints = "LongOnly")

all.equal(port@portfolio, myPort@portfolio)

Now with your numbers:

现在与你的数字:

mu <- c(SBI=0.05, SPI=0.1, LMI=0.075, MPI=0.06)
sigma <- matrix(c(0.02657429, 0.01805751, 0.02048764, 0.02110555, 0.01805751, 0.03781108, 0.03859943, 0.02959261, 0.02048764, 0.03859943, 0.04606304, 0.03043146, 0.02110555, 0.02959261, 0.03043146, 0.03880064), 4, 4, dimnames=list(names(mu), names(mu))) 
myLppData <- myPortfolioData(mu, sigma, lppAssets, defaultSpec)
myPort <- efficientPortfolio(myLppData, defaultSpec, constraints = "LongOnly")

Hope that helps!

希望会有帮助!

#3


0  

There is another way to write your own covariance estimator. This is explained in Portfolio Optimization with R/Rmetrics Update 2015, Diethelm Würtz, Tobias Setz, Yohan Chalabi, William Chen, Andrew Ellis, page 234.

还有另一种方法可以写出自己的协方差估计量。这在2015年R/Rmetrics更新的投资组合优化中得到了解释,Diethelm Wurtz, Tobias Setz, Yohan Chalabi, William Chen, Andrew Ellis,第234页。

You can do something like this:-

你可以这样做:-。

mu = c(0.05,0.1,0.075,0.06)
cov <- matrix(c(0.02657429, 0.01805751, 0.02048764, 0.02110555, 0.01805751, 0.03781108, 0.03859943, 0.02959261, 0.02048764, 0.03859943, 0.04606304, 0.03043146, 0.02110555, 0.02959261, 0.03043146, 0.03880064), 4, 4, dimnames=list(names(mu), names(mu))) 
lppAssets <- 100*LPP2005.RET[, c("SBI", "SPI", "LMI", "MPI")]

covtEstimator <- function (x, spec = NULL, ...) {
x.mat = as.matrix(x)
list(mu = mu, Sigma = cov) }   #Input your mean and covariance matrix here.

defaultSpec <- portfolioSpec()
setEstimator(defaultSpec) <- "covtEstimator"
setTargetReturn(defaultSpec) <- 0.06

myPort2 <- efficientPortfolio(lppAssets, defaultSpec, constraints = "LongOnly")

which also produce the same answer.

结果是一样的。

Title:
MV Efficient Portfolio 
Estimator:         covtEstimator 
Solver:            solveRquadprog 
Optimize:          minRisk 
Constraints:       LongOnly 

Portfolio Weights:
[1] 0.7316 0.1829 0.0000 0.0855

Covariance Risk Budgets:
[1] 0.1473 0.6156 0.0000 0.2370

Target Returns and Risks:
 mean     mu    Cov  Sigma   CVaR    VaR 
0.0205 0.0600 0.1986 0.1555 0.4805 0.3003 

Hope it is still not too late to answer this question! May be useful to others. Thanks

希望现在回答这个问题还不算太晚!可能对别人有用。谢谢

#1


1  

You need to do something like this:

你需要这样做:

library(quadprog)

d = rep(0,4); #4 - no. of stocks
A = rbind(rep(1,4), #1st const. --- sum of weights should be 1
                mu, #2nd const. --- returns should be positive
                diag(4) #3rd const ---- all the weights are positive   
        );
b = c(1, 0, rep(0,4) );
solve.QP(cov, d, t(A), b, meq=1)

#2


1  

I am not an expert in the fPortfolio package. But it looks like you need to define your own fPFOLIODATA object. In fPortfolio this is done in the portfolioData() function. So a quick and dirty solution might be to write your own function that doesn't do the covariance estimation but takes as input your estimated mu and sigma. So here is my solution:

我不是fPortfolio的专家。但是看起来您需要定义自己的fPFOLIODATA对象。在fPortfolio中,这是在portfolioData()函数中完成的。所以一个快速而棘手的解决方案可能是写出你自己的函数它不做协方差估计,而是作为你的估计和的输入。这就是我的解:

myPortfolioData <- function(mu, sigma, data, spec){
    if (is(data, "fPFOLIODATA")) 
        return(data)
    stopifnot(class(data) == "timeSeries")
    data = sort(data)
    nAssets = NCOL(data)
    names = colnames(data)
    if (is.null(names)) 
        names = paste("A", 1:nAssets, sep = "")
    Cov = cov(data)
    rownames(Cov) <- colnames(Cov) <- names
    .data = list(series = data, nAssets = nAssets, names = names)
    .statistics <- list(mean = colMeans(data), Cov = Cov, estimator = 'other', mu = mu, Sigma = covar);
    .tailRisk = spec@model$tailRisk
    new("fPFOLIODATA", data = .data, statistics =.statistics, tailRisk = .tailRisk)
}

Let's test if it gives the same results:

让我们来测试它是否给出了相同的结果:

library(fPortfolio)

#This is how you would usually do it
defaultSpec <- portfolioSpec()
setTargetReturn(defaultSpec) <- 0.06
lppAssets <- 100*LPP2005.RET[, c("SBI", "SPI", "LMI", "MPI")]
lppData <- portfolioData(data = lppAssets, spec = defaultSpec)
port <- efficientPortfolio(lppData, defaultSpec, constraints = "LongOnly")

#Now I am creating my own mu and sigma 
#In this case exactly the same as the estimation above to see if the results match  
mu <- c(SBI=0.0000406634, SPI=0.0841754390, LMI=0.0055315332, MPI=0.0590515119)
sigma <- matrix(c(0.015899554, -0.01274142,  0.009803865, -0.01588837,-0.012741418,  0.58461212, -0.014074691,  0.41159843,0.009803865, -0.01407469,  0.014951108, -0.02332223,-0.015888368,  0.41159843, -0.023322233,  0.53503263), 4, 4, dimnames=list(names(mu), names(mu))) 
myLppData <- myPortfolioData(mu, sigma, lppAssets, defaultSpec)
myPort <- efficientPortfolio(myLppData, defaultSpec, constraints = "LongOnly")

all.equal(port@portfolio, myPort@portfolio)

Now with your numbers:

现在与你的数字:

mu <- c(SBI=0.05, SPI=0.1, LMI=0.075, MPI=0.06)
sigma <- matrix(c(0.02657429, 0.01805751, 0.02048764, 0.02110555, 0.01805751, 0.03781108, 0.03859943, 0.02959261, 0.02048764, 0.03859943, 0.04606304, 0.03043146, 0.02110555, 0.02959261, 0.03043146, 0.03880064), 4, 4, dimnames=list(names(mu), names(mu))) 
myLppData <- myPortfolioData(mu, sigma, lppAssets, defaultSpec)
myPort <- efficientPortfolio(myLppData, defaultSpec, constraints = "LongOnly")

Hope that helps!

希望会有帮助!

#3


0  

There is another way to write your own covariance estimator. This is explained in Portfolio Optimization with R/Rmetrics Update 2015, Diethelm Würtz, Tobias Setz, Yohan Chalabi, William Chen, Andrew Ellis, page 234.

还有另一种方法可以写出自己的协方差估计量。这在2015年R/Rmetrics更新的投资组合优化中得到了解释,Diethelm Wurtz, Tobias Setz, Yohan Chalabi, William Chen, Andrew Ellis,第234页。

You can do something like this:-

你可以这样做:-。

mu = c(0.05,0.1,0.075,0.06)
cov <- matrix(c(0.02657429, 0.01805751, 0.02048764, 0.02110555, 0.01805751, 0.03781108, 0.03859943, 0.02959261, 0.02048764, 0.03859943, 0.04606304, 0.03043146, 0.02110555, 0.02959261, 0.03043146, 0.03880064), 4, 4, dimnames=list(names(mu), names(mu))) 
lppAssets <- 100*LPP2005.RET[, c("SBI", "SPI", "LMI", "MPI")]

covtEstimator <- function (x, spec = NULL, ...) {
x.mat = as.matrix(x)
list(mu = mu, Sigma = cov) }   #Input your mean and covariance matrix here.

defaultSpec <- portfolioSpec()
setEstimator(defaultSpec) <- "covtEstimator"
setTargetReturn(defaultSpec) <- 0.06

myPort2 <- efficientPortfolio(lppAssets, defaultSpec, constraints = "LongOnly")

which also produce the same answer.

结果是一样的。

Title:
MV Efficient Portfolio 
Estimator:         covtEstimator 
Solver:            solveRquadprog 
Optimize:          minRisk 
Constraints:       LongOnly 

Portfolio Weights:
[1] 0.7316 0.1829 0.0000 0.0855

Covariance Risk Budgets:
[1] 0.1473 0.6156 0.0000 0.2370

Target Returns and Risks:
 mean     mu    Cov  Sigma   CVaR    VaR 
0.0205 0.0600 0.1986 0.1555 0.4805 0.3003 

Hope it is still not too late to answer this question! May be useful to others. Thanks

希望现在回答这个问题还不算太晚!可能对别人有用。谢谢