Home > Blockchain >  reclassify columns according to score R
reclassify columns according to score R

Time:06-05

I am working with a df organized as follow

a = c("A","B","C","D")
b = c(55,3,5,0)
c = c(6, 22, 4.5, 9)
d = c(0.5, 44, 33, 87)
df = data.frame(t(rbind(a,b,c,d)))

It can represent scores of players A,B,C,D in successive runs (b,c,d) of a game.

I want to reclassify each column of df from the best score to the worst. Ideally this should be the expected df:

a b c d

A 1 3 4

B 3 1 2

C 2 4 3

D 4 2 1

I tried multiple ways to do it with command "order" or "rank" in a loop reading each column, but id does not give me the correct output (I mean...the one I want).

It looks a simple logic work but I'm stuck!! I very appreciate any help!

CodePudding user response:

You haven't shown what code you used but using an sapply loop across the three numeric columns with order produces:

sapply(df1[-1], order)
     b c d
[1,] 4 2 1
[2,] 2 3 3
[3,] 3 1 2
[4,] 1 4 4

sapply(df1[-1], order, decreasing=TRUE)
     b c d
[1,] 1 4 4
[2,] 3 1 2
[3,] 2 3 3
[4,] 4 2 1

(I did change the name of the data object because df is a legitimate R function name, as is dt for that matter.)

CodePudding user response:

Using the tidyverse, assuming a higer score is better for "b" and "d" and a lower score is better for "c":

    library(tidyverse)
    df = tribble(
      ~a, ~b, ~c, ~d, 
      "A", 55, 6, 0.5,
      "B", 3, 22, 44,
      "C", 5, 4.5, 33,
      "D", 0, 9, 87
    )
    
    df %>%
      mutate(
        across(c(b,d), ~ order(., decreasing = TRUE)),
        c = order(c)
        )

Output:

a         b     c     d
<chr> <int> <int> <int>
A         1     3     4
B         3     1     2
C         2     4     3
D         4     2     1

CodePudding user response:

Lots of ways to do this. Here is a data.table approach.

a = c("A","B","C","D")
b = c(55,3,5,0)
c = c(6, 22, 4.5, 9)
d = c(0.5, 44, 33, 87)
# df = data.frame(t(rbind(a,b,c,d)))   # NO, NO, NO!
df = data.frame(a,b,c,d)               # create df this way

library(data.table)
rankCols <- c('b', 'c', 'd')
setDT(df)[, c(rankCols):=lapply(.SD, \(x) frank(-x)), .SDcols=rankCols]
df

Sidebar: rbind(a,b,c,d) will create a matrix with rows formed from your vectors. But in R all elements of a matrix must have the same data type. R uses a least common denominator approach so the numerics are coerced to character.

  • Related