Статус обработки данных в процессе анализа данных очевиден для всех, и это также самая трудная задача, с которой сталкивается каждый специалист по данным.
В сценариях практических приложений, хотя SQL (профессиональный язык SQL etl) является предпочтительным звездным языком для обработки данных, он обладает хорошей производительностью, высокой эффективностью и легко развивает мышление на основе данных, но SQL не может справиться с задачей обработки данных для построения всего процесса. , и по-прежнему необходимо использовать другие инструменты анализа данных для более глубокого анализа.
Как профессиональный язык статистических вычислений, язык R, обработка данных является одной из его основных функций.На самом деле, каждая задача обработки имеет более одного набора решений на языке R (обычно это когда новички чувствуют, что содержание слишком много, когда они начать работу с языком R. Есть много причин, по которым невозможно начать), конечно, эти разные решения имеют большие различия в производительности и эффективности.
Трудно разумно выбрать набор собственных инструментов обработки данных, потому что это связано с привычками использования и затратами на миграцию.Например, если вы знакомы с базовой системой рисования языка R без сильной движущей силы, вы Возможно, вам не захочется тратить много времени на изучение ggplot 2. Если вы умеете писать циклы for/while, вам не захочется осваивать функцию группового применения, даже те пакеты параллельных вычислений с невероятной производительностью, вы будете использовать простые строки в начале. , видя, что пакет stringr сталкивается с проблемой обновления инструмента навыков...
Слишком много опций, это головокружение, и я сам столкнулся с этой путаницей.Чтобы не отвлекаться, я сначала составляю список возможностей - составляю список всех инструментов, которые могут выполнять ту же функцию, и делаю набор функциональных карт (также предварительное понимание). Затем выберите наиболее профессиональный набор в соответствии с текущей ситуацией, которую вы освоили, и постепенно обнаружьте недостатки существующей комбинации инструментов с течением времени и начните пытаться перейти на более эффективные и короткие инструменты, чтобы навыки обновлялись и переносились с спрос как движущая сила, более тщательный и явный.
Наиболее типичные миграции наборов навыков следующие:
基础字符串处理函数——stringr
绘图系统:plot——ggplot2
代码风格:函数嵌套——管道函数(`%>%`)
列表处理:list(自建循环)——rlist
json处理:Rjson+RJSONIO——jsonlite
数据抓取:RCurl+XML——httr+xml2
循环任务:for/while——apply——plyr::a_ply——并行运算(foreach、parallel)
切片索引:subset——dplyr::select+filter
聚合运算:aggregate——plyr::ddply+mutate——dplyr::group_by+summarize
数据联结:merge——plyr::join——dplyr::left/right/inner/outer_join
数据塑型:plyr::melt/dcast——tidyr::gather/spread
...
На самом деле, существует много типов путей повышения квалификации с аналогичными функциональными комбинациями, которые не указаны.Хотя миграция инструмента сопряжена с высокими затратами, особенно затратами времени и затратами на обучение, эффективный и краткий опыт работы с кодом, полученный после миграции, по-прежнему Очень круто, вышесказанное, особенно миграция функции конвейера, вызывает глубочайшее чувство, и больше нет сцены, где вещи, которые вы написали, перемежаются.
Сказав так много, что вы хотите делать после такого большого обхода? Да, я должен сегодня прокачать себя новыми навыками. Главный герой на этот раз
data.table
Высокопроизводительный пакет обработки данных на языке R, пакет может охватывать большую часть вышеупомянутой обработки данных, и операция очень абстрактна (абстрактность означает, что количество кода ужасно).
На самом деле, я давно общаюсь с data.table, и причина, по которой он не применялся глубоко, заключается в том, что его концепция слишком сильно отличается от других пакетов обработки данных.Можно сказать, что стоимость миграции очень высока. высока, и это почти восстановление навыков, а не миграция.
Однако по мере расширения поля зрения выясняется, что действительно необходимо понимать этот высокопроизводительный пакет.Хотя он немного подрывает традиционный стиль R, улучшения производительности и эффективности могут компенсировать это.
data.table
1. Производительность ввода-вывода:
Важная причина, по которой data.table вызывает восхищение, заключается в том, что его пропускная способность ввода-вывода не имеет себе равных среди многих пакетов языка R. Вот набор данных о велосипедных поездках в Нью-Йорке 1,6G в 2015 году в качестве примера для проверки его производительности. Xiaomi Instinct может выдержать бросок~_~
#清空内存
rm(list=ls())
gc()
#使用传统的I/O函数read_csv2进行导入:
setwd("D:/Python/citibike-tripdata/")
system.time(
mydata1 <- read.csv("2015-citibike-tripdata.csv",stringsAsFactors = FALSE,check.names = FALSE)
)
用户 系统 流逝
197.34 2.56 200.75
object.size(mydata1)
1914019808 bytes
数据量还是很大的,将近1.6G,900多万记录,16个字段。
Бедная машина, память и диск вот-вот лопнут~
Импорт с использованием функций ввода-вывода внутри data.table:
rm(list=ls())
gc()
library("data.table")
system.time(
mydata1 <- fread("2015-citibike-tripdata.csv")
)
Read 9937969 rows and 16 (of 16) columns from 1.606 GB file in 00:00:45
用户 系统 流逝
43.44 0.48 44.43
Пятикратная эффективность, 9 миллионов данных 1.606G за 45 секунд, все еще очень убедительна (хотя и не легендарная десятикратная производительность).
rm(list=ls())
gc()
2. Агрегация индексных срезов
Data.table предоставляет модель обработки данных, которая объединяет функции индексации строк, разделения столбцов и группировки.
DT[i,j,by]
Если этот процесс выполняется с помощью select ...... from ...... где ...... groupby ...... с помощью SQL, он, по крайней мере, выполняется пакетами в других базовых пакетах. Р.
dplyr::fliter() %>% select() %>% group_by() %>% summarize()
Хоть и можно оптимизировать код с помощью конвейерных функций, он все равно не может конкурировать с простотой data.table.
mydata <- fread("https://raw.githubusercontent.com/wiki/arunsrinivasan/flights/NYCflights14/flights14.csv")
Здесь используется онлайн-набор данных, содержащий всю информацию о рейсах из аэропортов Нью-Йорка в 2014 году.
class(mydata)
[1] "data.table" "data.frame"
После импорта с помощью функции fread он будет автоматически преобразован в объект data.table.Это высокопроизводительный объект данных, уникальный для data.table.Он также наследует традиционный класс фрейма данных data.frame, что означает, что он может включать множество методов фрейма данных и вызовы функций.
str(mydata)
一共253316条记录,17个字段。
"год" дата полета - год
"месяц" дата полета - месяц
"дневная" дата рейса - день
"dep_time" время отправления рейса
"dep_delay" продолжительность задержки рейса
"arr_time" время прибытия рейса
"arr_delay" время задержки прибытия рейса
отмена рейса «отменено»
"перевозчик"
"хвост"
"полет"
"происхождение" взлет
пункт назначения
"эфирное_время"
"расстояние"
расстояние
"час"
"мин"
индекс строки data.table
carrier <- unique(mydata$carrier)
[1] "AA" "AS" "B6" "DL" "EV" "F9" "FL" "HA" "MQ" "VX" "WN" "UA" "US" "OO"
tailnum <- sample(unique(mydata$tailnum),5)
[1] "N332AA" "N813MQ" "N3742C" "N926EV" "N607SW"
origin <- unique(mydata$origin)
[1] "JFK" "LGA" "EWR"
dest <- sample(unique(mydata$dest),5)
[1] "BWI" "OAK" "DAL" "ATL" "ALB"``
mydata[carrier == "AA" ]
#等价于
mydata[carrier == "AA",]
#行索引可以直接引用列表,无需加表明前缀,这一点儿数据框做不到,而且i,j,by三个参数对应的条件支持模糊识别,无论加“,”与否都可以返回正确结果。
mydata[carrier %in% c("AA","AS"),]
支持在行索引位置使用%in% 函数。
индекс столбца data.table
По сравнению с фреймом данных индекс столбца имеет большую разницу в опыте работы.Индекс столбца data.table отказывается от параметров векторизации в эпоху data.frame и использует параметр списка для индексации столбца.
mydata[,list(carrier,tailnum)]
Для удобства работы список здесь может быть упрощен до символа точки. который:
mydata[,.(carrier,tailnum)]
#但心里要清楚列索引接受的条件是含有列表的列表,而且这里的列表作为变量给出,而非data.frame时代的字符串向量。
Нет необходимости одновременно индексировать строки и столбцы.
mydata[carrier %in% c("AA","AS"),.(carrier,tailnum)]
Позиция индекса столбца не только поддерживает индекс имени столбца, но также напрямую поддерживает операции встроенной функции.
mydata[,.(flight/1000,carrier,tailnum)]
Поддержка создания нового столбца непосредственно в позиции индекса столбца, символ присваивания: =.
mydata[,delay_all := dep_delay+arr_delay]
#销毁某一列:
mydata[,delay_all := NULL]
Массовые новые столбцы:
mydata[,c("delay_all","delay_dif") := .((dep_delay+arr_delay),(dep_delay-arr_delay))]
等价于写法2:
mydata[,`:=`(delay_all = dep_delay+arr_delay,delay_dif =dep_delay-arr_delay )]
#销毁新建列:
mydata[,c("delay_all","delay_dif") := NULL]
Обратите внимание, что при создании нового столбца выше, если есть только один столбец, имя столбца относительно свободно, и его можно записать в виде строки или переменной.Однако при создании нескольких столбцов вы должны строго следовать шаблону, который Столбец слева называется строковым вектором, а столбец справа — списком.Конечно, вы также можете использовать второе обозначение.
DT[,`:=`(varname1 = statement1 ,varname1 = statement2)]
Вы можете напрямую использовать встроенные функции data.table.
mydata[carrier %in% c("AA","AS"),.N]
[1] 26876
.N是一个计数函数,相当于plyr中的count,或者基础函数中的length。
Основные статистические функции поддерживаются напрямую.
mydata[carrier %in% c("AA","AS"),.(sum(dep_delay),mean(arr_delay))]
V1 V2
1: 228913 5.263841
mydata[carrier %in% c("AA","AS"),.(dep_delay,mean(arr_delay))]
mydata[carrier %in% c("AA","AS") & dep_delay %between% c(500,1000),.(dep_delay,arr_delay)]
Когда весь столбец и агрегированное отдельное значение выводятся одновременно, может поддерживаться операция автоматического завершения.
Реальная мощь data.table раскрывается лишь постепенно, когда агрегатные функции используются с параметрами группировки в data.table.
mydata[,.(sum(dep_delay),mean(arr_delay)),by = carrier]
Мультигрупповая агрегация.
mydata[,.(sum(dep_delay),mean(arr_delay)),by = .(carrier,origin)]
Многогрупповой подсчет.
mydata[,.N,by = .(carrier,origin)]
Пользовательское имя:
mydata[,.(dep_delay_sum = sum(dep_delay),arr_delay_mean = mean(arr_delay)),by = carrier]
mydata[,.(dep_delay_sum = sum(dep_delay),arr_delay_mean = mean(arr_delay)),by = .(carrier,origin)]
mydata[,.(carrier_n = .N),by = .(carrier,origin)]
Сортировка данных:
Сортировать строки:
setorder(mydata,carrier,-arr_delay)
Функция setorder воздействует на сами данные mydata и работает без вывода. Если вы хотите запускать и выводить одновременно, вы можете добавить [] в конце
setorder(mydata,carrier,-arr_delay)[]
Эта функция чем-то похожа на основную функцию, но оператор заключен в круглые скобки. (а
Сортировать столбец:
sample(names(mydata),length(names(mydata)))
[1] "arr_time" "air_time" "distance" "dep_time" "dest" "arr_delay" "month" "min" "tailnum" "origin"
[11] "year" "hour" "cancelled" "flight" "day" "carrier" "dep_delay"
setcolorder(mydata,sample(names(mydata),length(names(mydata))))
mydata[carrier == "AA",
lapply(.SD, mean),
by=.(carrier,origin,dest),
.SDcols=c("arr_delay","dep_delay")
]
Приведенный выше синтаксис добавляет новые параметры .SDcols и .SD. На первый взгляд это сбивает с толку. На самом деле, он основан на трех измерениях несущей, источника и пункта назначения для выполнения средней операции над определенными столбцами каждого подблока.
Логика выполнения здесь следующая:
by=.(carrier,origin,dest) 先按照三个维度进行全部的分组;
.SDcols=c("arr_delay","dep_delay")则分别在筛选每一个子数据块儿上的特定列;
lapply(.SD, mean)则将各个子块的对应列应用于均值运算,并返回最终的列表。
Объединение данных:
Метод слияния данных в data.table очень прост;
DT <- data.table(x=rep(letters[1:5],each=3), y=runif(15))
DX <- data.table(z=letters[1:3], c=runif(3))
Установите соответствующие первичные ключи:
setkey(DT,x)
setkey(DX,z)
DT[DX]
Это так просто Логика выполнения соединения заключается в том, что внутренняя сторона — это левая таблица, а внешняя сторона — правая таблица, поэтому это DX левое соединение DT
Если первичный ключ не задан, необходимо явно объявить внутренний параметр on и указать первичный ключ подключения.Единственный первичный ключ должен иметь одинаковое имя в левой и правой таблицах.
Конечно, если вы не привыкли к такому использованию или привыкли использовать слияние, data.table по-прежнему поддерживается, поскольку он наследует фрейм данных и поддерживает все вызовы функций для фрейма данных.
Левая рука использует R правую руку Python Series - слияние данных и присоединение
Преобразование длины и ширины:
Преобразование аспекта по-прежнему поддерживает функции плавления/dcast в plyr и функции сбора/распространения в tidyr.
В этой статье описаны только основные общие функции data.table.Если вы хотите более гибкого и расширенного использования в период обучения, пожалуйста, также асинхронные официальные документы.
Левая рука использует R правую серию Python - формирование данных и преобразование длины и ширины