En général, xtfrm()
est la fonction générique permettant d'obtenir un tableau numérique qui trie comme le tableau d'entrée donné. Un tri décroissant peut alors être effectué en triant avec la valeur négative de xtfrm()
. (C'est exactement la façon dont, par exemple dplyr desc()
est mis en œuvre).
Par exemple, avec les données en question :
df <- read.table(text = "
P1 P2 P3 T1 T2 T3 I1 I2
2 3 5 52 43 61 6 b
6 4 3 72 NA 59 1 a
1 5 6 55 48 60 6 f
2 4 4 65 64 58 2 b
", header = TRUE)
df[order(-xtfrm(df$I1), df$I2), ]
#> P1 P2 P3 T1 T2 T3 I1 I2
#> 1 2 3 5 52 43 61 6 b
#> 3 1 5 6 55 48 60 6 f
#> 4 2 4 4 65 64 58 2 b
#> 2 6 4 3 72 NA 59 1 a
Cette approche peut être généralisée dans une fonction R de base pour trier des cadres de données par des colonnes données, qui accepte également une valeur vectorielle decreasing
argument. De ma réponse à cette question récente :
sortdf <- function(x, by = colnames(x), decreasing = FALSE) {
x[do.call(order, Map(sortproxy, x[by], decreasing)), , drop = FALSE]
}
sortproxy <- function(x, decreasing = FALSE) {
as.integer((-1)^as.logical(decreasing)) * xtfrm(x)
}
Et avec les données de l'exemple actuel, nous obtenons (bien sûr) :
sortdf(df, by = c("I1", "I2"), decreasing = c(TRUE, FALSE))
#> P1 P2 P3 T1 T2 T3 I1 I2
#> 1 2 3 5 52 43 61 6 b
#> 3 1 5 6 55 48 60 6 f
#> 4 2 4 4 65 64 58 2 b
#> 2 6 4 3 72 NA 59 1 a