Выбрать / Получить имена всех столбцов, которые имеют отрицательное значение от 0 до 10 - PullRequest
0 голосов
/ 16 мая 2019

Для фрейма данных я хотел бы получить имена или выбрать все столбцы, которые имеют отрицательные значения в определенном диапазоне. Этот пост подходит довольно близко, но он перебирает строки, что невозможно для моих данных.Кроме того, если я сохраню это решение, оно станет списком, в котором я бы предпочел вектор.Например, для следующего набора данных:

library(data.table)
df <- fread(
     "A   B   D   E  iso   year   
      0   1   1   NA ECU   2009   
      1   0   2   0  ECU   2009   
      0   0   -3  0  BRA   2011   
      1   0   4   0  BRA   2011   
      0   1   7   NA ECU   2008   
     -1   0   1   0  ECU   2008   
      0   0   3   2  BRA   2012   
      1   0   4   NA BRA   2012",
  header = TRUE
)

Я хотел бы иметь имена всех столбцов, которые имеют отрицательные значения от 0 до 10 (в данном примере это A и D).Что было бы самым простым решением для достижения этой цели?Все остальное, равное data.table, было бы предпочтительным.

Ответы [ 2 ]

2 голосов
/ 16 мая 2019

Другой tidyverse вариант:

df %>% 
   group_by(iso,year) %>% 
   keep(~any(.x>-10 & .x<0 & !is.na(.x))) %>% 
   names()
 "A" "D"

EDIT : Для обработки факторов используйте mutate_if. Мы могли бы сделать то же самое (хотя я думаю, что группировка будет лучше):

  df %>% 
   mutate_if(is.factor,as.character) %>% 
   purrr::keep(~any(.x>-10 & .x<0 & !is.na(.x))) %>% 
   names()
[1] "A" "D"

Значения:

df %>% 
  group_by(iso,year) %>% 
   keep(~any(.x>-10 & .x<0 & !is.na(.x)))
# A tibble: 8 x 2
      A     D
  <int> <int>
1     0     1
2     1     2
3     0    -3
4     1     4
5     0     7
6    -1     1
7     0     3
8     1     4
2 голосов
/ 16 мая 2019

Одна tidyverse возможность может быть:

 df %>%
 gather(var, val, -c(5:6)) %>%
 group_by(var) %>%
 summarise(res = any(val[!is.na(val)] > -10 & val[!is.na(val)] < 0))

  var   res  
  <chr> <lgl>
1 A     TRUE 
2 B     FALSE
3 D     TRUE 
4 E     FALSE

Чтобы выбрать только числовые столбцы:

df %>%
 select_if(is.numeric) %>%
 gather(var, val) %>%
 group_by(var) %>%
 summarise(res = any(val[!is.na(val)] > -10 & val[!is.na(val)] < 0)) 

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

Вы можете сделать это также с помощью base R:

df <- Filter(is.numeric, df)
cond <- as.logical(colSums(df > -10, na.rm = TRUE) *
                    colSums(df < -0, na.rm = TRUE))
colnames(df[, cond])

[1] "A" "D"

или записанным в виде «одной строки»:

df <- Filter(is.numeric, df)
colnames(df[, as.logical(colSums(df > -10, na.rm = TRUE) * colSums(df < -0, na.rm = TRUE))])

Пример данных:

df <- read.table(text = 
 "A   B   D   E  iso   year   
      0   1   1   NA ECU   2009   
      1   0   2   0  ECU   2009   
      0   0   -3  0  BRA   2011   
      1   0   4   0  BRA   2011   
      0   1   7   NA ECU   2008   
     -1   0   1   0  ECU   2008   
      0   0   3   2  BRA   2012   
      1   0   4   NA BRA   2012", 
 header = TRUE,
 stringsAsFactors = FALSE)
...