#' ELPDweight calculates the probability that each model is best for prediction
#' @title Return the probability of models compared with loo being the best for prediction
#' @author Marc Girondot \email{marc.girondot@@gmail.com}
#' @return A vector with the probabilities
#' @param loos A named list of loos
#' @param nreplicates Number of replicates.
#' @description Calculate the probability of models compared with loo being the best for prediction. 
#' It uses simulation using the pointwise LOO log-predictive densities. This preserves the correlation 
#' between models, because all models are evaluated on the same observations. This is the approach 
#' recommended by Aki Vehtari when uncertainty in model comparison matters.
#' @family AIC
#' @examples
#' \dontrun{
#' model1_loo <- loo::loo(model1)
#' model2_loo <- loo::loo(model2)
#' ELPDweight(list(model1=model1_loo, model2=model2_loo))
#' }
#' @export

ELPDweight <- function (loos = stop("A named list of loo data must be provided."), 
                                         nreplicates = 10000) 
{
  elpd_mat <- sapply(loos, function(x) x$pointwise[,"elpd_loo"])
  
  N <- nrow(elpd_mat)
  K <- ncol(elpd_mat)
  
  best <- numeric(nreplicates)
  
  for(s in 1:nreplicates){
    
    # Bayesian bootstrap weights
    w <- rexp(N)
    w <- w/sum(w)
    
    # weighted ELPD
    elpd_sim <- colSums(elpd_mat * w)
    
    best[s] <- which.max(elpd_sim)
  }
  
  prob <- table(best)/nreplicates
  prob_ec <- rep(0, K)
  names(prob_ec) <- as.character(1:K)
  prob_ec[names(prob)] <- as.numeric(prob)
  if (!any(is.null(names(loos)))) names(prob_ec) <- names(loos)
  return(prob_ec)
}

