web-dev-qa-db-fra.com

Statistiques sommaires de deux variables de facteurs ou plus?

Ceci est mieux illustré avec un exemple

str(mtcars)
mtcars$gear <- factor(mtcars$gear, labels=c("three","four","five"))
mtcars$cyl <- factor(mtcars$cyl, labels=c("four","six","eight"))
mtcars$am <- factor(mtcars$am, labels=c("manual","auto")
str(mtcars)
tapply(mtcars$mpg, mtcars$gear, sum)

Cela me donne le mpg de sommation par équipement. Mais disons que je voulais une table 3x3 avec un équipement sur le dessus et de cyliser sur le côté et 9 cellules avec les somme bivariées dans, comment puis-je obtenir cela "intelligemment".

Je pourrais aller.

tapply(mtcars$mpg[mtcars$cyl=="four"], mtcars$gear[mtcars$cyl=="four"], sum)
tapply(mtcars$mpg[mtcars$cyl=="six"], mtcars$gear[mtcars$cyl=="six"], sum)
tapply(mtcars$mpg[mtcars$cyl=="eight"], mtcars$gear[mtcars$cyl=="eight"], sum)

Cela semble encombrant.

Alors, comment ferais-je apporter une 3ème variable dans le mélange?

C'est un peu dans l'espace que je pense. Statistiques sommaires à l'aide de DDPLY

Mise à jour Cela me fait là-bas, mais ce n'est pas joli.

aggregate(mpg ~ am+cyl+gear, mtcars,sum)

À votre santé

13
nzcoops

Je pense que les réponses déjà sur cette question sont des options fantastiques, mais je voulais partager une option supplémentaire basée sur le package dplyr (ceci est venu pour moi parce que j'enseigne une classe maintenant où nous utilisons dplyr Pour la manipulation de données, je voulais donc éviter d'introduire des élèves à des fonctions de base spécialisées de base comme tapply ou aggregate).

Vous pouvez regrouper autant de variables que vous voulez utiliser group_by Fonction et résume ensuite les informations de ces groupes avec summarize. Je pense que ce code est plus lisible à un nouveau venu que l'interface de formule de aggregate, donnant des résultats identiques:

library(dplyr)
mtcars %>%
  group_by(am, cyl, gear) %>%
  summarize(mpg=sum(mpg))
#       am   cyl  gear   mpg
#    (dbl) (dbl) (dbl) (dbl)
# 1      0     4     3  21.5
# 2      0     4     4  47.2
# 3      0     6     3  39.5
# 4      0     6     4  37.0
# 5      0     8     3 180.6
# 6      1     4     4 168.2
# 7      1     4     5  56.4
# 8      1     6     4  42.0
# 9      1     6     5  19.7
# 10     1     8     5  30.8

Avec deux variables, vous pouvez résumer avec une variable sur les lignes et l'autre sur les colonnes en ajoutant un appel à la fonction spread de l'emballage tidyr:

library(dplyr)
library(tidyr)
mtcars %>%
  group_by(cyl, gear) %>%
  summarize(mpg=sum(mpg)) %>%
  spread(gear, mpg)
#     cyl     3     4     5
#   (dbl) (dbl) (dbl) (dbl)
# 1     4  21.5 215.4  56.4
# 2     6  39.5  79.0  19.7
# 3     8 180.6    NA  30.8
9
josliber

J'aime la réponse de Josh pour cela, mais reshape2 peut également fournir un bon cadre pour ces problèmes:

library(reshape2)

#use subset to only grab the variables of interest...
mtcars.m <- melt(subset(mtcars, select = c("mpg", "gear", "cyl")), measure.vars="mpg")
#cast into appropriate format
dcast(mtcars.m, cyl ~ gear, fun.aggregate=sum, value.var="value")

   cyl three  four five
1  four  21.5 215.4 56.4
2   six  39.5  79.0 19.7
3 eight 180.6   0.0 30.8
4
Chase

La réponse contient la même sortie à l'aide de la fonction TAPPLY et agrégat.

Je voudrais ajouter des informations à la réponse de Josh O'Brien. L'utilisateur peut soit utiliser une fonction agrégée ou en fonction de la sortie. Afin d'utiliser plus d'une variable de facteur dans TAPPLY, on peut utiliser la méthode Josh a montré.

Loading DataSet

data("mtcars")

En utilisant tapply

with(mtcars, tapply(mpg, list("Cylinder#"=cyl, "Gear#"=gear), sum))

La sortie du code ci-dessus est

        Gear#
Cylinder#     3     4    5
    4     21.5 215.4 56.4
    6     39.5  79.0 19.7
    8    180.6    NA 30.8

Utilisation de la fonction agrégée

with(mtcars, aggregate(mpg, list(Cylinder = cyl, Gear =  gear), sum))

Sortie de la fonction agrégée

    Cylinder Gear  x
1        4    3  21.5
2        6    3  39.5
3        8    3 180.6
4        4    4 215.4
5        6    4  79.0
6        4    5  56.4
7        6    5  19.7
8        8    5  30.8

Maintenant, si l'utilisateur veut la même sortie que la fonction d'agrégat mais en utilisant TAPPLY.

as.data.frame(as.table(with(mtcars, tapply(mpg, list("Cylinder#"=cyl, "Gear#"=gear),
sum))))

Sortie de la fonction TAPPLY

   Cylinder. Gear.  Freq
1         4     3  21.5
2         6     3  39.5
3         8     3 180.6
4         4     4 215.4
5         6     4  79.0
6         8     4    NA
7         4     5  56.4
8         6     5  19.7
9         8     5  30.8

NA peut être conservé ou supprimé selon les besoins.

3
Maulik Chaudhary