intro_r/script/replace_values.html

1.0 MiB
Raw Blame History

<html> <head> </head>

Criar uma coluna com caracteres indicando qual célula em três colunas da tabela apresenta maior valor

José

2021-11-13

Remover objetos

rm(list = ls())

Pergunta

Pergunta do grupo R-brasil no Telegram

Quero criar a coluna “maior” com o nome da coluna que tem o maior valor na linha

Solução usando R base

Criar uma tabela com três colunas de tipo numérico com valores entre 0 a 1

A função runif cria 10 valores entre 0 a 1 se os valores máximo e mínimo não são definidos dentro do parêntese

df <- data.frame(a = runif(10),
                 b = runif(10),
                 c = runif(10))

Criar vectores definindo a condição lógica esperada em cada caso

Se a coluna “a” apresentar o maior valor, então o vector “a_maior” terá um elemento “TRUE”, do contrário, o elemento será “FALSE”…

a_maior <- with(df, a > b & a > c)

b_maior <- with(df, b > a & b > c)

c_maior <- with(df, c > a & c > b)

Criar uma coluna na tabela com valores de cero em todas as linhas

df$maior <- 0

Indexar um caractere dentro da coluna “maior” indicando a coluna que apresentou o maior valor em cada linha da tabela

Inserir “a” na posição em que a coluna “a” apresentou o maior valor; ou seja: quando a condição lógica foi igual a “TRUE”

df$maior[a_maior] <- "a"

df$maior[b_maior] <- "b"

df$maior[c_maior] <- "c"

Criar uma função simples para executar a tarefa

maior_valor <- function (df, a, b, c, ...) {

    a_maior <- with(df, a > b & a > c)
    b_maior <- with(df, b > a & b > c)
    c_maior <- with(df, c > a & c > b)

    linhas <- nrow(df)
    coluna <- rep(0, times = linhas)

    coluna[a_maior] <- "a"
    coluna[b_maior] <- "b"
    coluna[c_maior] <- "c"

    df$V1 <- coluna

    return(df)
}

A coluna “maior” é o resultado de indexar com a primeira parte do código e a coluna “V1” resulta de aplicar a função na tabela

maior_valor(df, a, b, c)

Usando o pacote dplyr

library(dplyr)

dfd <- tibble(p_col = runif(10),
              s_col = runif(10),
              t_col = runif(10))

A função rowwise aplica a função which.max em todas as linhas. case_when é usado para substituir o número da coluna pelo nome

dfd %>%
    rowwise() %>%
    mutate(m = which.max(c(p_col, s_col, t_col)),
           m = case_when(
               m == 1 ~ names(.)[1],
               m == 2 ~ names(.)[2],
               m == 3 ~ names(.)[3],
               TRUE ~ as.character(m)
           ))
</html>