Скорость вычислений в R?

16

Мне было поручено перевести одну из наших текущих больших стохастических моделей из SAS на новый язык. Лично я предпочитаю традиционный скомпилированный язык, но PI хочет, чтобы я проверил R, который я никогда не использовал. Наша мотивация для выведения модели из SAS заключается в том, что (1) многие люди не имеют к ней доступа, поскольку SAS стоит дорого, (2) мы стремимся отойти от интерпретируемого языка, и (3) SAS работает медленно тип модели у нас есть.

Для (1) очевидно, что R удовлетворяет потребности быть свободным. Для (2) в идеале мы хотели бы создать исполняемый файл, но R обычно используется как язык сценариев. Я вижу, что кто-то недавно выпустил компилятор R - это было хорошо принято? Легко ли пользоваться? Мы бы не хотели, чтобы пользователь сам загружал R. Для (3) наша проблема с SAS - все время, затрачиваемое на запись / чтение наборов данных ввода / вывода. Наша модель требует больших вычислительных ресурсов, и мы часто ограничены временем выполнения. (Например, нередки случаи, когда кто-то угоняет компьютеры людей в выходные дни для выполнения пробежек.) У нас есть похожая модель, построенная на Фортране, которая не имеет такой же проблемы, потому что вся работа выполняется в памяти. Как работает R? Будет ли это так же, как SAS, в том, что он работает в шагах данных, чтение и запись файлов? Или он может делать манипуляции с массивами в памяти?

Мелисса
источник
Обычно вы можете ускорить sas, выполнив всю свою работу за один шаг данных. Это должно сократить время ввода-вывода, поскольку вы фактически считываете данные только один раз. Использование большого количества процедур также замедлит вас. Например, если вы моделируете многократный вызов proc glm или proc logistic (скажем, для начальной загрузки), быстрее создать огромный набор данных и использовать оператор by, чем вызывать много вызовов proc (например, с помощью макроса% do). если программа SAS хорошо, вы не должны быть проблемы времени выполнения из - за чтения и outputing файлов (по крайней мере , не больше , чем другие программы
probabilityislogic
Кроме того, вы можете использовать временные массивы в шагах данных sas аналогично тому, как вы использовали бы матрицы в R.
вероятностный

Ответы:

18

R работает в памяти - поэтому ваши данные должны помещаться в память для большинства функций.

Пакет компилятора, если я думаю о том, о чем вы думаете ( пакет компилятора Люка Тирни, поставляемый с R), не то же самое, что компилируемый язык в традиционном смысле (C, Fortran). Это байтовый компилятор для R в смысле байт-кода Java, выполняемого виртуальной машиной Java, или байтовой компиляции кода LISP Emacs. Он не компилирует R-код в машинный код, а подготавливает R-код в байт-код, чтобы его можно было использовать более эффективно, чем необработанный R-код для интерпретации.

Обратите внимание, что если вы хорошо сформировали Фортран, вы, вероятно, могли бы иметь лучшее из обоих миров; R может вызывать скомпилированные фортрановские процедуры.

Восстановить Монику - Дж. Симпсон
источник
Благодарность! Приятно знать, что я мог бы получить отличную графику R и вызывать скомпилированные процедуры на Фортране. Это может быть ответом!
Мелисса
2
Просто подробнее о замечании Гэвина о памяти: смотрите раздел «Большая память» в этом представлении задач CRAN, если вы работаете с большими наборами данных: cran.r-project.org/web/views/HighPerformanceComputing.html
Брэндон Бертельсен,
1
Также думаю, что важно отметить, что Rcpp, вероятно, может быть использован для увеличения производительности.
Брэндон Бертельсен
Rcpp полезен, чтобы обернуть C ++ для использования в / с R. Он помогает процессу (безмерно), но все еще использует базовые инструменты R для вызова скомпилированного кода. Если у ОП уже есть коды Фортрана или навыки Фортрана, Rcpp может оказаться менее полезным.
Восстановить Монику - Дж. Симпсон
13

Я использовал в SASтечение 15 лет, и начал использовать Rсерьезно последние 6 месяцев, с некоторыми возиться в нем на пару лет вперед. С точки зрения программирования, осуществляет R ли манипулирование данными напрямую, нет эквивалента DATAили PROC SQLпроцедур, потому что они не нужны (последний более эффективен, SASкогда требуется много манипуляций с данными из внешних источников данных, например административных данных). Это означает, что теперь я понимаю, что манипулирование данными происходит быстрее Rи требует гораздо меньше кода.

Основная проблема, с которой я столкнулся, - это память. Не все пакеты R допускают WEIGHTспецификации типов, поэтому, если у вас есть SASнаборы данных с переменными, используемыми в выражениях FREQили REPLICATE, у вас могут возникнуть проблемы. Я посмотрел на ffи bigmemoryпакетов в R , но они не появляются , чтобы быть совместимым со всеми пакетами R, поэтому если у вас есть очень большие наборы данных , которые требуют анализа, которые относительно редко, и были объединены, могут возникнуть проблемы с памятью.

Для автоматизации, если у вас есть, SAS macrosвы должны быть в состоянии запрограммировать эквивалент в Rи запустить как пакетный.

Для кодирования Rя использовал Notepad++и установил язык R, а теперь открываю радости R Studio. Оба эти продукта бесплатны и делают разметку языка как улучшенный SASсинтаксис GUI (я только когда-либо использовал экран синтаксиса в SAS).

Существует веб-сайт и соответствующая книга для людей, которые меняются с SASна R. Я нашел их полезными для того, чтобы попытаться понять, как перевести некоторые SASкоманды в R.

Обновление: одна вещь , которая отвезла меня орехи , когда подходит к R, что Rне берет на себя все это набор данных ( data frameв Rпросторечии), потому что это не статистический пакет таким образом , что SAS, SPSS, Stata, и т.д.. Так, например, мне потребовалось некоторое время, чтобы заставить ifоператоры работать, потому что я продолжал получать помощь для ifоператоров с векторами (или, возможно, матрицами), тогда как мне нужно было ifоператор, который работал с data frames. Таким образом, страницы справки, вероятно, нужно читать более внимательно, чем обычно, потому что вам нужно проверить, что команда, которую вы хотите выполнить, будет работать с вашим типом объекта данных.

То, что до сих пор сводит меня с ума, когда я изучаю новую Rкоманду (например, метод анализа в предоставленном пакете), заключается в том, что справка по командам часто не является полностью автономной. Я пойду на страницу справки, чтобы попытаться выучить команду, и в ней часто ...содержатся замечания по использованию . Иногда пытаясь понять, что может или должно пойти туда, куда ...ведет меня в рекурсивный цикл. Относительная краткость справочных заметок, из SASкоторых приводятся подробные примеры синтаксиса и рабочие примеры с объяснением исследования на этом примере, была довольно большим шоком.

Мишель
источник
2
+1 Пожалуйста, рассмотрите возможность обновления нашей мета-ветки, где мы собрали ссылки на ресурсы программного обеспечения статистики. Там есть один ответ для R и другой для SAS: оба извлекут выгоду из ссылки на r4stats.com. (Эта ветка на самом деле является частью нашего FAQ. Мы надеемся, что она будет актуальной и полезной.)
whuber
1
R также имеет пакеты, которые поддерживают доступ к SQL через драйверы RODBC или SQLite.
DWin
1
Я согласен с вашими комментариями о помощи R. Я фактически указал на то, что вы говорите в одном из списков рассылки R много лет назад. Ответ не был положительным. Справедливости ради, я (а), вероятно, не очень хорошо выразился, и не привел никаких конкретных примеров и (б) не занимался этим вопросом. Подводя итог, проблема 1 является слишком сложными примерами и включает в себя слишком много несвязанных понятий. Сложные примеры в порядке, но должны следовать простым примерам. Проблема 2 заключается в том, что практически нет аннотаций или объяснений того, что делают примеры.
Фахим Митха
Относительно R "помощь" напоминает что-то, что мой босс сказал мне. «Вы изучаете R, делая это с кем-то, кто уже знает, что R сидит рядом с вами за компьютером»,
вероятностный
А для всех остальных есть книги и переполнение стека. Да, изучать R самостоятельно довольно сложно, по крайней мере, для меня.
Мишель
10

R это язык программирования. Работает не по шагам. Он делает все, что вы хотите, потому что это всего лишь язык программирования, раб для ваших желаний, выраженный языком фигурных скобок и двоеточий.

Думайте об этом как о Fortran или C, но с неявной векторизацией, чтобы вам не приходилось зацикливаться на массивах, и динамическим управлением памятью, чтобы вам не приходилось использовать malloc () или объявлять размеры массивов в любое время.

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

Вы противоречите себе, утверждая, что модель требует значительных вычислительных ресурсов, но SAS работает медленно из-за операций ввода-вывода ... Конечно, одно или другое ...

Если у вас уже есть что-то подобное в Фортране, и вы говорите, что хотите отойти от интерпретируемого языка, то почему бы просто не сделать это и в Фортране?

Компилятор R может привести к некоторому ускорению, но если ваш код R хорошо написан, вы не получите ничего слишком масштабного - не то же самое, что написать его на C или Fortran.

Spacedman
источник
Ах, я не объяснил себя хорошо. Он интенсивно манипулирует наборами данных, что в SAS означает слишком много времени, затрачиваемого на ввод-вывод. Моим первоначальным предложением был Fortran, но PI заинтересован в том, чтобы мы перешли на R, поэтому он хотел, чтобы я проверил это. Благодарность!
Мелисса
7

Я понимаю, что по умолчанию SAS может работать с моделями, размер которых превышает объем памяти, но в случае с R это не так, если вы специально не используете такие пакеты, как biglm или ff.

Тем не менее, если вы выполняете работу с массивами в R, которая может быть векторизована, это будет очень быстро - возможно, в два раза быстрее, чем программа C в некоторых случаях, но если вы делаете что-то, что не может быть векторизовано, тогда это будет выглядеть довольно медленный. Чтобы дать вам пример:

# create a data.frame with 4 columns of standard normally distributed RVs
N <- 10000

# test 1
system.time( {df1 <- data.frame(h1=rnorm(N),
                h2=rpois(N, lambda=5),
                h3=runif(N),
                h4=rexp(N))
} )
# about 0.003 seconds elapsed time

# vectorised sum of columns 1 to 4
# i.e. it can work on an entire column all at once
# test 2
system.time( { df1$rowtotal1 <- df1$h1 + df1$h2 + df1$h3 + df1$h4 })
# about 0.001 seconds elapsed time

# test 3
# another version of the vectorised sum
system.time( { df1$rowtotal2 <- rowSums(df1[,c(1:4)]) })
# about 0.001 seconds elapsed time

# test 4
# using a loop... THIS IS *VERY* SLOW AND GENERALLY A BAD IDEA!!! :-)
system.time( {
        for(i in 1:nrow(df1)) {
                df1$rowtotal3 <- df1[i,1]+ df1[i,2] + df1[i,3] + df1[i,4]
        }
} )
# about 9.2 seconds elapsed time

Когда я увеличил N в десять раз до 100 000, я отказался от теста 4 через 20 минут, но тесты 1: 3 заняли 61, 3 и 37 миллисекунд каждый

Для N = 10 000 000 время испытаний 1: 3 составляет 3,3 с, 0,6 с и 1,6 с.

Обратите внимание, что это было сделано на ноутбуке i7 и на 480 МБ для N = 10 миллионов, память не была проблемой.

Для пользователей в 32-разрядных окнах существует ограничение в 1,5 ГБ для R независимо от того, сколько у вас памяти, но такого ограничения нет для 64-разрядных окон или 64-разрядных Linux. В наши дни память очень дешевая по сравнению со стоимостью часа моего времени, поэтому я просто покупаю больше памяти, а не трачу время, пытаясь обойти это. Но это предполагает, что ваша модель поместится в памяти.

Шон
источник
1
(+1) Спасибо за предложение полезных иллюстраций, Шон!
whuber
3

(2) в идеале мы хотели бы создать исполняемый файл, но R обычно используется как язык сценариев

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

О()rle()

Так что будь очень осторожен. После первых попыток у вас наверняка возникнет отвращение к R, потому что вы найдете его медленным, со странным синтаксисом и т. Д. Как только вы его узнаете, это может быть очень эффективным инструментом. Вы даже можете закончить, написав свои методы на R как предварительный этап для программирования C / C ++. Конечным этапом будет изучение API R для создания предварительно скомпилированных функций, и вы станете мастером R :)

Элвис
источник
2

Манипулирование массивом в памяти - большая вещь для SAS, по-видимому. Я не знаю особенностей, касающихся R, но я предполагаю, что R работает в памяти по умолчанию, поскольку пакеты расширения памяти для R, ff и bigmemory перемещают данные из памяти на диск. У меня есть указатели для вас, если вы хотите улучшить скорость или использование памяти. Чтобы повысить скорость, вам сначала нужно использовать R по назначению, то есть: векторизовать ваш код и использовать компиляцию байтового кода. (Также: по возможности избегайте операций копирования в память.) Во-вторых, используйте предоставленный профилировщик кода Rprof (), чтобы идентифицировать медленные патчи в вашем коде, и переписать их на C или C ++, если это необходимо. Если вам нужно больше памяти, вы можете использовать аргумент skip в функции read.table () для одновременного считывания в ваших данных чанка, а также вы можете использовать пакет, такой как RMySQL, который добавляет утилиты манипулирования базой данных в R. Если вам нужно еще больше памяти и вы можете позволить себе сопутствующее снижение скорости, вы можете использовать пакет snow для запуска R параллельно. (Подробности об этом и многое другое можно найти в книге Нормана Мэтлоффа «Искусство программирования на R», опубликованной в конце прошлого года. Подробную информацию о пакетах, упомянутых здесь, можно найти в Интернете.)

Жан-Виктор Кот
источник