управлять значением столбца на основе имен строк в R - PullRequest
0 голосов
/ 01 августа 2020

Я пытаюсь изменить значение столбца на основе имен строк, любая помощь будет оценена.

data(mtcars)
    mtcars$gear1 <- factor(mtcars$gear, levels = c(3,4,5))
    my.mean <- function(x) if(is.numeric(x)) mean(x) else prop.table(table(x))
    B <- setNames(as.data.frame(unlist(lapply(mtcars, FUN = my.mean))), "mean")
    
    
    class(B)
    row.names(B)
    put.per <- c("gear1.3", "gear1.4", "gear1.5")
    
    sapply(row.names(B),function(x){
       if(x %in% put.per) paste(B$mean, "%", sep = "")
       })

Ожидаемый ответ

              mean
mpg      20.090625
cyl       6.187500
disp    230.721875
hp      146.687500
drat      3.596563
wt        3.217250
qsec     17.848750
vs        0.437500
am        0.406250
gear      3.687500
carb      2.812500
gear1.3   0.468750%
gear1.4   0.375000%
gear1.5   0.156250%

заранее большое спасибо

Ответы [ 2 ]

2 голосов
/ 01 августа 2020

Использование имен строк обычно не является хорошей идеей, так как это удаляет информацию из ячеек вашего фрейма данных. Лучше сохранить исходные имена переменных в столбце обрабатываемого набора данных.

В dplyr v1.0.0.0 код для этого является компактным.

d <- mtcars %>% 
       summarise(across(everything(), mean)) %>% 
       pivot_longer(names_to="variable", values_to="mean", cols=everything())
d
# A tibble: 11 x 2
   variable    mean
 * <chr>      <dbl>
 1 mpg       20.1  
 2 cyl        6.19 
 3 disp     231.   
 4 hp       147.   
 5 drat       3.60 
 6 wt         3.22 
 7 qsec      17.8  
 8 vs         0.438
 9 am         0.406
10 gear       3.69 
11 carb       2.81 

Если вы должны использовать имена строк, а не столбец в таблице:

row.names(d) <- d$variable
d <- d %>% select(-variable)

Я только что видел ваши gear.x строк. Что вы пытаетесь там сделать?

Обновить

Полное решение:

mtcars %>% 
  summarise(across(everything(), mean)) %>% 
  pivot_longer(names_to="variable", values_to="mean", cols=everything()) %>% 
  mutate(mean=as.character(mean)) %>% 
  bind_rows(
    mtcars %>% 
      group_by(gear) %>% 
      summarise(mean=sprintf("%8.6f%%", n()/nrow(.))) %>% 
      mutate(variable=paste0("gear.", gear)) %>% 
      select(-gear)
  )
# A tibble: 14 x 2
   variable mean      
   <chr>    <chr>     
 1 mpg      20.090625 
 2 cyl      6.1875    
 3 disp     230.721875
 4 hp       146.6875  
 5 drat     3.5965625 
 6 wt       3.21725   
 7 qsec     17.84875  
 8 vs       0.4375    
 9 am       0.40625   
10 gear     3.6875    
11 carb     2.8125    
12 gear.3   0.468750% 
13 gear.4   0.375000% 
14 gear.5   0.156250% 

Лично я бы не форматировал проценты по шестеренке в виде символов внутри фрейма данных / таблицы. Я бы сохранил их как двойные (и добавил бы столбец индикатора, чтобы определить тип данных, представленных в mean, и переименовать mean в нечто более представительное, например statistic - в этом случае столбец индикатора может принимать значения mean и percentage например) и представлены в процентах только на выходе. (И я думаю, вам нужно умножить на 100, чтобы получить проценты. В настоящее время у вас есть дроби, обозначенные как проценты.)

1 голос
/ 01 августа 2020

Здесь вам не понадобится sapply или какой-либо другой тип l oop. Вы можете найти индекс строки, где присутствуют значения put.per, и изменить их на paste0.

inds <- rownames(B) %in% put.per
B$mean[inds] <- paste0(B$mean[inds], "%")
B

#              mean
#mpg      20.090625
#cyl         6.1875
#disp    230.721875
#hp        146.6875
#drat     3.5965625
#wt         3.21725
#qsec      17.84875
#vs          0.4375
#am         0.40625
#gear        3.6875
#carb        2.8125
#gear1.3   0.46875%
#gear1.4     0.375%
#gear1.5   0.15625%

Однако обратите внимание, что столбец может содержать данные только одного типа, поэтому здесь все значения будут к символу, так как мы добавляем знак %.

...