в Развлекаюсь

dplyr — легкая работа с данными

Сегодня опишу пакет dplyr, после изучения которого, манипуляции с данными упростятся до безобразия. Велосипед изобретать не буду и использую существующие статьи 1 и 2 по той же теме. Вот еще и на русском. Все гениальное просто, поэтому почти возможные варианты работы пакета базируются на нескольких функциях. Основные из них:
Select() выбирает заданные столбцы;
Filter() отбирает желаемые строки;
Arrange() сортирует строки в заданном порядке;
Mutate() создает новые столбцы из существующих данных;
Summarise() находит интересующие значения.

Установим собственно пакет, если еще не сделали этого
install.packages("dplyr")
И загрузим его
library(dplyr)
Воспользуемся данными о качестве воздуха в Нью-Йорке, измеренными в период с май по сентябрь далекого 1973 года
library(datasets)
Посмотрим на данные
head(airquality)
Ну данные как данные, ничего особенного
Ozone Solar.R Wind Temp Month Day
1 41 190 7.4 67 5 1
2 36 118 8.0 72 5 2
3 12 149 12.6 74 5 3
4 18 313 11.5 62 5 4
5 NA NA 14.3 56 5 5
6 28 NA 14.9 66 5 6

Смысл понятен, но информацию о данных в более удобоваримом виде можно получить используя функцию dplur glimplse(). Команда транспонирует данные (поменяет местами строки и столбцы) и укажет количество наблюдений и переменных.
glimpse(airquality)
Вот так это всё выглядит
Observations: 153
Variables: 6
$ Ozone (int) 41, 36, 12, 18, NA, 28, 23, 19, 8, NA, 7, 16, 11, 14, 18, 14, 34, 6, ...
$ Solar.R (int) 190, 118, 149, 313, NA, NA, 299, 99, 19, 194, NA, 256, 290, 274, 65, ...
$ Wind (dbl) 7.4, 8.0, 12.6, 11.5, 14.3, 14.9, 8.6, 13.8, 20.1, 8.6, 6.9, 9.7, 9.2...
$ Temp (int) 67, 72, 74, 62, 56, 66, 65, 59, 61, 69, 74, 69, 66, 68, 58, 64, 66, 5...
$ Month (int) 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, ...
$ Day (int) 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20...

Select
Теперь перейдем к функционалу вышеуказанных команд. Начнем с отбора нужной нам информации, отфильтруем, так сказать, ненужное. Функция select() выберет требуемые столбцы. Она работает также, как и базовая команда subset(), однако включает в себя удобные подфункции contains(), starts_with() и ends_with(), которые облегчают определение и выбор желаемых столбцов.
Выберем только столбцы со скоростью ветра и днём
select(airquality, Wind, Day)
В этом и следующих двух примерах для компактности я покажу только первые три строчки результата.
Wind Day
1 7.4 1
2 8.0 2
3 12.6 3

Выберем все столбцы, имена которых содержат латинскую «o»
select(airquality, contains("o"))
Ozone Solar.R Month
1 41 190 5
2 36 118 5
3 12 149 5

Посмотрим на столбцы, имена которых начинаются с «Oz»
select(airquality, starts_with("Oz"))
Мы-то догадываемся, что в результате будет только столбец с концентрацией озона
Ozone
1 41
2 36
3 12

Filter
Продолжим отбирать интересующую нас информацию. Функция filter() оставит только строки, которые соответствуют заданным условиям. Ну например, выберем все наблюдения, когда температура поднималась выше 92 градусов по фаренгейту.
filter(airquality, Temp > 92)
Получаем
Ozone Solar.R Wind Temp Month Day
1 NA 259 10.9 93 6 11
2 76 203 9.7 97 8 28
3 118 225 2.3 94 8 29
4 84 237 6.3 96 8 30
5 85 188 6.3 94 8 31
6 73 183 2.8 93 9 3
7 91 189 4.6 93 9 4

Приятно, что условия можно комбинировать как душе угодно. Вот хочется мне узнать, когда в июне значения измеренной солнечной радиации превышали 300 Лэнгли. Да проще некуда
filter(airquality, Month == 6 & Solar.R > 300)
Такая картина вырисовывается
Ozone Solar.R Wind Temp Month Day
1 39 323 11.5 87 6 10
2 NA 332 13.8 80 6 14
3 NA 322 11.5 79 6 15

Arrange
Функция arrange() отсортирует данные по переменным. Можно сортировать сразу по нескольким параметрам, а также в порядке возрастания или убывания. Для примера расположим наблюдения по месяцам по убыванию и дням по возрастанию.
arrange(airquality, desc(Month),Day)
В результате (только первые 5 строк)
Ozone Solar.R Wind Temp Month Day
1 96 167 6.9 91 9 1
2 78 197 5.1 92 9 2
3 73 183 2.8 93 9 3
4 91 189 4.6 93 9 4
5 47 95 7.4 87 9 5

Mutate
Переходим к моей любимой команде mutate(), которая позволяет добавлять новые переменные (столбцы). Добавим столбец с температурой в цельсиях, который назовем TempInC
mutate(airquality, TempInC = (Temp - 32) * 5 / 9)
Легко и просто (опять покажу только первые 5 строк результата)
Ozone Solar.R Wind Temp Month Day TempInC
1 41 190 7.4 67 5 1 19.44444
2 36 118 8.0 72 5 2 22.22222
3 12 149 12.6 74 5 3 23.33333
4 18 313 11.5 62 5 4 16.66667
5 NA NA 14.3 56 5 5 13.33333

Summarise
Функция summarise() позволяет получить быстрое представление о всех данных в одном значении, например, посчитать среднее арифметическое. В комбинации с командой группировки данных group_by() можно легко находить интересующие значения для группированных данных. Простой пример: посчитаем среднюю температуру в каждом из месяцев.
summarise(group_by(airquality, Month), mean_monthly_temp=mean(Temp, na.rm = TRUE))
na.rm = TRUE просто не учитывает все отсутствующие данные при расчете среднего. В итоге имеем
Month mean_monthly_temp
(int) (dbl)
1 5 65.54839
2 6 79.10000
3 7 83.90323
4 8 83.96774
5 9 76.90000

В рамках summarise() помимо нахождения среднего арифметического, можно использовать и другие команды, возвращающие скалярные значения, например min(), max(), sum(), sd(), median().

Pipe
Оператор %>% позволяет совершать последовательные операции без сохранения промежуточных результатов. Допустим, мы хотим увидеть, какая максимальная температура в градусах цельсия была зарегистрирована в летние месяцы.
airquality %>%
filter(Month == c(6,7,8)) %>% #оставляем только летние месяцы
mutate(TempInC = (Temp - 32) * 5 / 9)%>% # считаем температуру в градусах цельсия
group_by(Month) %>% # группируем по месяцам
summarise(max_temp_C = max(TempInC, na.rm = TRUE)) # находим максимальное значение температуры для каждого из летних месяцев

В итоге получаем
Month max_temp_C
(int) (dbl)
1 6 33.33333
2 7 31.66667
3 8 36.11111

Незаменимая команда, когда переменных и наблюдений достаточно много.

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

Write a Comment

Комментарии