R-пакеты nlt / adlift / ebayesthresh используют огромные объемы памяти;как улучшить производительность? - PullRequest
8 голосов
/ 12 марта 2011

Все началось с R пакета Мне нужно было использовать плохо ( 'nlt' ), у которого есть 2 другие (довольно большие) зависимости пакета ( 'adlift') , 'ebayesthresh' ). Мне нужно было проанализировать выборку данных около 4000 баллов.

Алгоритмы создают множество «скрытых» векторов, поэтому, даже если на первый взгляд вы подумаете, что у вас достаточно памяти для загрузки выборки данных и ее обработки, все становится быстро. На данный момент я должен упомянуть, что у меня есть и Ubuntu x64, и Windows x64 с 4 ГБ оперативной памяти.

Из чистого любопытства и мазохизма, я думаю, я решил попробовать его на экземпляре Amazon EC2 . В итоге я попробовал несколько из них и остановился на очень большой памяти 1016 * 17,1 ГБ с большим объемом памяти с 6,5 ЭБУ, когда мне снова не хватило памяти, и Ubuntu убила мою работающую функцию.

Я закончил с использованием подхода split-apply-Combine с 'snowall' , 'foreach' и 'doSMP', Я разбил свои данные на части, обработал каждый кусок и объединил результаты. Слава Богу, что я рад, и мы живем. Образец был проанализирован менее чем за 7 минут на моем ноутбуке.

Полагаю, я должен быть счастлив, но 7 минут - это еще много, и я бы не хотел снова прыгать в Amazon EC2, если только на самом деле не осталось ничего, что могло бы сократить время выполнения.

Я провел некоторые исследования, пакеты 'bigmemory' и 'ff' для R, по-видимому, позволяют значительно ускорить работу, особенно если я использую данные, сохраненные в файле.

Пакет 'nlt' принимает в качестве входных данных только векторы, а 'bigmemory' , например, имеет свой специальный тип данных, big.matrix. Даже если бы я волшебным образом мог передавать big.matrixes в пакет 'nlt' , это все равно оставляет много новых распределений векторов со стандартными функциями R, которые жестко запрограммированы в пакете и его зависимостях.

Я продолжаю думать о аспектно-ориентированном программировании / исправлении обезьян , и мне удалось найти, по-видимому, единственный пакет R для такой вещи, 'r-connect' .

Теперь, как я вижу, у меня есть 2 основных варианта:

  • вручную переписать пакет nlt и все его функциональные зависимости из двух других пакетов и вместо стандартных функций list (), matrix () и т. Д. Использовать функции 'bigmemory' , кошмар в создание.
  • заменить стандартный список R, матрицу и т. Д. На 'bigmemory' функции

Я прыгаю на акулу? Кто-нибудь еще может предложить другое решение или поделиться подобным опытом?

1 Ответ

4 голосов
/ 12 марта 2011

Другим вариантом будет профилирование использования памяти этими 3 пакетами, удаление любых избыточных данных и удаление объектов, когда они больше не нужны.

UPDATE:
nlt не слишком сложно; в основном это функции adlift и EbayesThresh, так что я бы взглянул на эти два пакета.

Возьмем, например, adlift / R / Amatdual.R: Adual и Hdual инициализируются в начале функции Amatdual, но они никогда не индексируются в функции; они полностью воссозданы позже.

Adual <- matrix(0, n - steps + 1, n - steps + 1)
Hdual <- matrix(0, n - steps, n - steps + 1)
...
    Hdual <- cbind(diag(length(newpoints) - 1), lastcol)
...
Adual <- rbind(Hdual, as.row(Gdual))

Нет необходимости в этих двух начальных распределениях.

adlift и nlt также имеют несколько вариантов использования apply, которые можно переключить на ряд / столбец Средство / Сумма. Я не уверен, насколько это поможет с использованием памяти, но это будет быстрее. Т.е .:

apply(foo, 1, sum)   # same as rowSums(foo)
apply(foo, 2, sum)   # same as colSums(foo)
apply(foo, 1, mean)  # same as rowMeans(foo)
apply(foo, 2, mean)  # same as colMeans(foo)
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...