Извлечение записей в фрейме данных, соответствующих n наименьшим положительным значениям и n наибольшим отрицательным значениям определенной переменной в r

Представьте, что у меня есть таблица, подобная следующей.

set.seed(12)
table = 
  data.frame(
    value = rnorm(n = 10), 
    par = runif (n = 10, min = - 1, max = 1)
  )

Как я могу извлечь записи value и par, которые соответствуют двум наименьшим значениям par выше нуля и двум самым большим значениям ниже нуля? Я хотел бы получить что-то вроде

out = 
  data.frame(
    value = c(-0.2722960, -0.1064639, -0.3153487, 0.4280148),
    par = c(-0.464112814, - 0.121141350, 0.009535904, 0.339638592)
  )

Я был бы признателен, если бы это можно было сделать с помощью dplyr, чтобы иметь возможность делать это для больших фреймов данных с группирующими переменными.

На всякий случай вам обязательно следует оценить свои шансы (и последствия) получить 0-значения для par, мне очень нравится, как Адриано решает эту проблему.

margusl 26.04.2024 18:35
Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
2
1
69
3
Перейти к ответу Данный вопрос помечен как решенный

Ответы 3

А как насчет фильтрации значений выше 0, сортировки значений и получения первых двух строк?

library(dplyr)

out <- table %>%
  filter(par > 0) %>%     
  arrange(par) %>%         
  head(2) %>%               
  bind_rows(                
    table %>% 
      filter(par < 0) %>%     
      arrange(desc(par)) %>%  
      head(2)                 
  )

> out
       value          par
1 -0.3153487  0.009535904
2  0.4280148  0.339638592
3 -0.1064639 -0.121141350
4 -0.2722960 -0.464112814
Ответ принят как подходящий

Если вы включите par >= 0 в свою группу, вы можете выбрать 2 минимальных абсолютных значения с помощью slice_min(abs(par), n = 2):

library(dplyr, warn.conflicts = FALSE)
set.seed(12)
table = 
  data.frame(
    value = rnorm(n = 10), 
    par = runif (n = 10, min = - 1, max = 1)
  )

table |> 
  group_by(pos = par >= 0) |>
  slice_min(abs(par), n = 2) |>
  ungroup()
#> # A tibble: 4 × 3
#>    value      par pos  
#>    <dbl>    <dbl> <lgl>
#> 1 -0.106 -0.121   FALSE
#> 2 -0.272 -0.464   FALSE
#> 3 -0.315  0.00954 TRUE 
#> 4  0.428  0.340   TRUE

Created on 2024-04-25 with reprex v2.1.0

Другая альтернатива:

# Toy data `my_table` at the end
aux <- my_table$par[my_table$par != 0] %>% 
  split(sign(.)) %>% 
  sapply(\(x) head(x[order(abs(x))], 2))

my_out <- my_table[my_table$par %in% aux, ]
rm(aux)

Ввод, вывод:

# Input
> arrange(my_table, par)
        value          par
1  -0.9567445 -0.804293921
2  -0.6282552 -0.622826146
3  -1.9976421 -0.564353914
4  -1.4805676 -0.563265665
5  -0.2722960 -0.464112814 # 
6  -0.1064639 -0.121141350 # 
7   9.0000000  0.000000000 # The presence of zero doesn't affect the output
8  -0.3153487  0.009535904 # 
9   0.4280148  0.339638592 # 
10 -0.9200052  0.419660932
11  1.5771695  0.575672695

# Output
> my_out
       value          par
1 -0.2722960 -0.464112814
2 -0.1064639 -0.121141350
3 -0.3153487  0.009535904
4  0.4280148  0.339638592

Данные игрушки:

my_table <- structure(list(
  value = c(
    -1.48056759491936, 1.57716947155863, -0.956744479084269, -0.920005247558641, 
    -1.99764209693134, -0.27229604424923, -0.315348711467784, -0.628255236517538, 
    -0.106463884872094, 0.428014802202354, 9), 
  
  par = c(
    -0.56326566496864, 0.575672694947571, -0.804293920751661, 0.419660932384431, 
    -0.564353913534433, -0.464112814050168, 0.00953590357676148, -0.622826146427542, 
    -0.121141349896789, 0.339638591744006, 0)), 
  
  class = "data.frame", row.names = c(NA, -11L))

Другие вопросы по теме

Предупреждение о производительности: DataFrame сильно фрагментируется при добавлении дополнительных столбцов
Как я могу преобразовать столбец данных Pandas в дату и время, если формат дробных секунд несовместим?
Как суммировать группировку в пандах с повторяющимися данными, сохраняя при этом другие столбцы
R: Более эффективный способ создания нового столбца фрейма данных, содержащего максимальное значение из строки
Как получить общую сумму на основе определенных столбцов, содержащих одно и то же значение
Установите значение матрицы равным 0, если имена строк и столбцов начинаются с одного и того же префикса
Как создать столбец фрейма данных, который представляет собой список из нескольких отдельных записей столбца?
Создать список уникальных комбинаций наборов данных для удаления дубликатов
Применить множественную функцию суммирования к столбцам: summarise_all: объект «список» нельзя заставить ввести «двойной»
Суперсложные манипуляции с наборами данных