Bonjour,
Je suis bloqué sur une ligne de code. je ne comprends pas ce qu'elle fait !
merci pour vos remarquesCode:
1
2
3
4
5
6 res = sapply(n:length(x), function(i, ...) FUN(x[(i - n + 1):i], ...)) if (!trim) { res = c(rep(NA, (n - 1)), res) }
Version imprimable
Bonjour,
Je suis bloqué sur une ligne de code. je ne comprends pas ce qu'elle fait !
merci pour vos remarquesCode:
1
2
3
4
5
6 res = sapply(n:length(x), function(i, ...) FUN(x[(i - n + 1):i], ...)) if (!trim) { res = c(rep(NA, (n - 1)), res) }
Bonjour,
Il y a deux blocs d'instructions dans ton exemple.
Pour rendre les choses un peu plus lisibles :
Le problème, c'est que pour le premier, il est impossible de dire ce que ça fait, ne sachant pas ce que fait la fonction FUN (ni d'ailleurs ce qu'il y a dans x et n).Code:
1
2
3
4
5
6
7
8
9
10 res <- sapply(n:length(x), function(i, ...) { FUN(x[(i - n + 1):i], ...) }) if (!trim) { res <- c(rep(NA, (n - 1)), res) }
Pour le deuxième bloc également il faudrait savoir ce que représentent les variables.
voici toute la fonction :
Code:
1
2
3
4
5
6
7 #Def fonction de fenetre gilssante rollFun = function(x, n = 9, FUN, trim = TRUE, na.rm = FALSE,...){x = as.vector(x) if (na.rm) x = as.vector(na.omit(x)) res = sapply(n:length(x), function(i, ...) FUN(x[(i - n + 1):i], ...)) if (!trim) res = c(rep(NA, (n - 1)), res) res}
Bonjour ouinih,
Tout d'abord, la fonction "rollFun" est-elle une fonction d'un package R (si oui, lequel)?
Sinon, d'après ce que j'ai compris, c'est la fonction "sapply" qui vous pose problème, c'est bien cela?
Alors, pour le morceau de code suivant :
On prend le vecteur des éléments n à length(x) (= longueur du vecteur x), par exemple si n=9 et x a une longueur de 12, on va avoir le vecteur : 9 10 11 12 .Code:
1
2
3
4
5 res <- sapply(n:length(x), function(i, ...) { FUN(x[(i - n + 1):i], ...) })
Et on applique à chacun des éléments de ce vecteur (9 10 11 et 12 dans mon exemple) la fonction définit comme suit :
Cette fonction est en fait la fonction "FUN" (en argument de ta fonction "rollFun") MAIS appliquée uniquement aux éléments de x compris entre le (i - n + 1)ème et le ième.Code:
1
2
3
4 f<-function(i, ...) { FUN(x[(i - n + 1):i], ...) }
Par exemple, si on reprend le cas où n=9 et x a 12 éléments.
On va d'abord appliquer la fonction f pour i=9 ie. la fonction "FUN" va être appliquée pour x[ 9 - 9 + 1 ] = x[1] , x[2], ... , x[9], puis dans un second temps on va appliquer la fonction f pour i=10 ie. la fonction "FUN" va être appliquée pour x[ 10 - 9 + 1 ] = x[2] , x[3], ... , x[9], etc... jusqu'à i=12.
Bien sûr, sans connaître plus de détails sur la fonction "FUN", difficile de savoir de quelle forme seront les résultats en sortie dans l'élément "res" (cela dit, au vue de la suite du code, je suppose qu'il s'agit d'un vecteur).
Pour info, la fonction "sapply" retourne un vecteur ou une matrice.
Voilà, j'espère que ceci vous éclairera un peu (mais pas sûr que ça soit bien clair, désolée :/ ). Sinon, pour plus d'infos sur la fonction "sapply", il est possible de jeter un oeil à son aide via ?sapply , et le mieux c'est de faire quelques tests sur des exemples basiques afin d'en comprendre le fonctionnement.
Sinon, concernant l'autre morceau de code qui semblait vous poser problème :
Ici on teste si l'élément "trim" est "FALSE" ( !trim = NON trim = [ trim == FALSE ] ), et si c'est le cas, on va ajouter un vecteur contenant (n-1) "NA" au début du vecteur "res" (obtenu précédemment).Code:
1
2
3
4 if (!trim) { res <- c(rep(NA, (n - 1)), res) }
Voilà, en espérant que ceci vous aide un peu à avancer, sinon n'hésitez pas à poser d'autres questions, et si éventuellement vous avez un exemple concret sur lequel appliquer la fonction "rollFun", cela nous facilitera peut-être la tâche pour vous aider.
Sur ce, bonne continuation :)
Cordialement,
A.D.
OK, c'est plus clair comme ça !
Ce que fait cette fonction (comme le suggère d'ailleurs le commentaire), c'est d'appliquer une fonction (FUN) sur x, en appliquant une fenêtre glissante de largeur n.
Par exemple pour le calcul d'une moyenne mobile :
Trim indique s'il faut ou non remplir les NAs au début (pas de moyenne mobile calculable sur les éléments 0 et 1 puisque le premier n'existe pas).Code:
1
2
3
4 > x <- 1:5 > > rollFun(x, n=2, FUN=mean, trim=FALSE) [1] NA 1.5 2.5 3.5 4.5
Ensuite, la moyenne est faite sur 1 et 2, puis 2 et 3, etc.
Le sapply revient en quelque sorte à faire une boucle for mais en nettement plus efficace.
Bon pour l'explication du sapply, je me suis fait grillé :aie:
Mais juste pour reformuler rapidement et plus dans la logique de R, je dirais que si
- i == 9 : la fonction FUN s'applique sur
Code:x[ (9 - 9 + 1):9 ] == x[1:9]
- i == 10 : FUN s'applique sur
Code:x[ (10 - 9 + 1):10 ] == x[2:10]
- ...
- i == lenght(x) : FUN s'applique sur
c'est à dire jusqu'au dernier élément de x (x[4:12]).Code:x[ (lenght(x) - 9 + 1):lenght(x) ]
Le sapply va donc appliquer cette recette pour chaque valeur de
Code:n:length(x) == c(9, 10, 11, 12)
Merci bcp à vous deux...
bonne soirée