J'écris une fonction pour calculer l'indice de diversité de Shannon. J'ai des données larges avec le pourcentage d'observations pour chaque valeur comme variables séparées, chaque ligne représentant un site différent. J'aurai entre 2 et 7 variables selon l'ensemble de données. Pour chaque ligne, je veux calculer l'indice d'information.
.
J'ai une fonction de boucle, mais elle est assez lente et je cherche de l'aide pour la vectoriser. Je suis également heureux pour une solution de style tidyverse.
J'ai envisagé d'utiliser le entropy
mais il semble s'attendre à ce que les données soient sous forme longue, et bien que je puisse étendre mes données, cela semble inutilement lent. J'ai actuellement 20 000 sites avec des centaines ou des milliers d'observations par site qui ont déjà été résumées dans les distributions en pourcentage au format large. Cette question fonctionne de la même manière avec les données longues.
Exemple de données
# Wide data, between 2 and 7 columns recording the percent of observations with each value, example using 3
df <- data.frame(
site = 1:3,
l1 = c(.33, .5, 0),
l2 = c(.33, .5, 0),
l3 = c(.33, 0, 1)
)
Fonction de la boucle actuelle
entropy <- function(df, vars) {
entropy_calc <- function(df, i, vars) {
sum <- 0
for (j in vars) {
x <- df[i,j]
if(x != 0) { # skip zeros
sum <- sum + x * log(x)
}
}
return(-sum)
}
entropy <- rep(NA, nrow(df))
for(i in 1:nrow(df)) {
entropy[i] <- entropy_calc(df, i, vars)
}
return(as.numeric(entropy))
}
df$entropy <- entropy(df, 2:4)