Завантажте відразу кілька пакетів


174

Як я можу завантажувати купу пакетів відразу, не переробляючи команду вимагати знову і знову? Я спробував три підходи, всі з яких руйнуються і горять.

В основному, я хочу поставити вектор імен пакунків функції, яка буде їх завантажувати.

x<-c("plyr", "psych", "tm")

require(x)
lapply(x, require)
do.call("require", x)

Відповіді:


251

Кілька перестановок запропонованих функцій спрацьовують, але лише якщо ви вказали character.onlyаргумент TRUE. Короткий приклад:

lapply(x, require, character.only = TRUE)

@Tommy & daroczig - Класно. Це набагато чистіше рішення. Я залишу свою справу лише для нащадків, а також того, що це свідчить про те, чому спроби ОП не спрацювали.
Josh O'Brien

4
Ви можете скористатись частковою відповідністю символів і піти з нахлестом (x, вимагати, ch = T) або навіть скупою (x, вимагати, c = T)
Dason

@daroczig Цей код завантажує пакунки, але чому він дає такі попереджувальні повідомлення: 1: У бібліотеці (пакет, lib.loc = lib.loc, character.only = TRUE, logic.return = TRUE,: пакет не називається 'x' 2: В, якщо (! завантажено) {: умова має довжину> 1, і буде використовуватися лише перший елемент
Ануша

@Anusha: Я не маю уявлення про банкомат, що ти маєш у своєму x?
daroczig

23
Буде добре, якщо R :: base додав цей lapplyвихідний трюк library(). Будьте чудові, щоб могли сказати:library(c("plyr", "umx"))
час

58

CRAN пакет pacman , що я підтримую ( в співавторстві з Dason Kurkiewicz) може зробити це:

Таким чином користувач міг зробити:

## install.packages("pacman")
pacman::p_load(dplyr, psych, tm) 

і якщо пакет відсутній p_load, завантажте його з CRAN або Bioconductor.


7
+1! Чому ви вибрали коротке ім’я p_load? Більш описова назва, наприклад, load_packagesробить наміри функції більш чіткими.
Пол Хіемстра

19
Тому що p означає пакет. Кожна функція в упаковці, яка є корисною та експортованою, починається з p_. Плюс ми схильні трохи використовувати бібліотеку, і це додаткові 7 символів. 7 символів x ~ 1000000 час використання функції x .5 секунд на символ = 3500000 секунд. Це 58333,33 хвилини, 972,2222 години або 40,50926 днів життя програміста, які ми повернули їм :-) У будь-якому випадку наша мета - перейти до CRAN до 1 лютого
Тайлер Рінкер

3
Приблизно на рік, але ми нарешті подали до CRAN. Повинен піднятися через кілька днів. @trinker (або я) не забудьте змінити це, коли воно стане загальнодоступним.
Дейсон

5
@Tyler Я знаю, що я запізнююсь на роки, але я вважаю ваше обґрунтування p_префікса досить сумнівним. Якщо проблемою є терміновість, видаліть p_префікс повністю. Насправді, такі префікси, як правило, відмовляються від інших мов з поважних причин (я сказав Я, що вони однакові щодо його fct_дурниць у форцах). Це особливо актуально, оскільки передбачуване використання пакету має кваліфікований простір імен ( pacman::).
Конрад Рудольф

5
@TylerRinker Вибачте за те, що ведете боротьбу з цим питанням, але я справді вважаю, що спільнота R тут просто неправильна, і практично будь-яка інша сучасна мова розуміє це правильно: Ви кажете "Це захищає від конфліктів у просторі імен". - Але це для чого простори імен! Завдання авторів пакунків полягає в тому, щоб навчити людей правильно користуватися пакунками, а не відповідати їх неохайній практиці програмування.
Конрад Рудольф

24

Для цього слід зробити фокус:

lapply(x, FUN = function(X) {
    do.call("require", list(X)) 
})

(Ключовим бітом є те, що argsаргументом в do.call(what, args) повинен бути список --- навіть якщо він містить лише один елемент!)


16

Для тих, хто хоче одночасно встановлювати та завантажувати пакети, я натрапив на цю функцію за цим посиланням

# ipak function: install and load multiple R packages.
# check to see if packages are installed. Install them if they are not, then load them into the R session.

ipak <- function(pkg){
new.pkg <- pkg[!(pkg %in% installed.packages()[, "Package"])]
if (length(new.pkg)) 
    install.packages(new.pkg, dependencies = TRUE)
sapply(pkg, require, character.only = TRUE)
}

# usage
packages <- c("ggplot2", "plyr", "reshape2", "RColorBrewer", "scales", "grid")
ipak(packages)

Здрастуйте, я створив файл R з вашого фрагменту. Коли я запускаю цей сценарій на службі Amazon EMR, він дає мені наступний вихід, як зазначено в наступній URL-адресі. pastie.org/10402378#3,10-11,13 .
Рубін Порваль

9

Альтернативний варіант походить від пакета easypackages. Після встановлення ви можете завантажувати пакунки найбільш інтуїтивно:

libraries("plyr", "psych", "tm")

У пакет також входить функція встановлення декількох пакетів:

packages("plyr", "psych", "tm")

Довідка тут .


Назва функції досить заплутане / заплутане. "Бібліотека" у libraryфункції позначає місце, де встановлені пакети: бібліотека пакетів . Завантажувати кілька пакетів через librariesсенс немає. Наявність окремої функції, packagesяка робить щось інше, просто погіршує це. Я знаю, що називання - це важка проблема в інженерії програмного забезпечення, але насправді. Ці імена особливо погані.
Конрад Рудольф

2
@KonradRudolph Я не погоджуюся, що назва librariesне має сенсу. Це множина libraryта libraryзавантажує один пакет; librariesзавантажує безліч пакетів. Якщо ви вважаєте, що libraryце означає "завантаження з вашої єдиної бібліотеки", і поширити це на librariesзначення "завантаження з декількох бібліотек", то це, можливо, неінтуїтивно, але це не є наміром; Я був би дуже задоволений назвою libraries.
Джеймі S

@JamieS Але це все ще (як правило) завантаження з однієї бібліотеки. Ви, мабуть, плутаєте бібліотеку та пакет (який, справедливо кажучи, став загальним для R): "Бібліотека R", як було зазначено в моєму попередньому коментарі, стосується місця (місць) (каталогу / каталогів), де встановлені пакети R . У прикладі цієї відповіді "plyr", "psych" і "tm" не є бібліотеками: вони є пакетами.
Конрад Рудольф

4

Ви можете просто скористатися пакетом lubripack, і він акуратно встановить нові пакети, а потім завантажить їх у один рядок.

lubripack("plyr", "psych", "tm")

Ось результат після запуску вище коду в RStudio.

введіть тут опис зображення

Як встановити пакет:

Запустіть код нижче, щоб завантажити пакет і встановити його з GitHub. Не потрібно мати обліковий запис GitHub.

library(devtools)
install_github("espanta/lubripack")

5
Я б здогадався, використовуючи зображення замість тексту
The Unfun Cat

3
Це також не дає відповіді на питання таким чином, на який уже не було відповідей, і, здається, здебільшого це самореклама.
Тайлер Рінкер

Ви маєте рацію, я намагався неявно відповісти на питання. Давайте зробимо це явним сподіванням, що це може відповісти на питання.
Еспанта

@TylerRinker Як це зараз?
Еспанта

3

Спираючись на рішення daroczig, якщо ви не хочете вказувати список як вхід, який ви можете використовувати

# Foo
mLoad <- function(...) {
  sapply(sapply(match.call(), as.character)[-1], require, character.only = TRUE)
}

# Example 
mLoad(plyr, dplyr, data.table)

... що коротше, ніж

lapply(list('plyr', 'dplyr', 'data.table'), require, character.only = TRUE)

2

Я використовую таку функцію:

mrip <- function(..., install = TRUE){
    reqFun <- function(pack) {
        if(!suppressWarnings(suppressMessages(require(pack, character.only = TRUE)))) {
            message(paste0("unable to load package ", pack,
                           ": attempting to download & then load"))
            install.packages(pack)
            require(pack, character.only = TRUE)
        }
    }
    lapply(..., reqFun)
}

Це намагається завантажити, а якщо не вдалося встановити, а потім спробуйте завантажити ще раз.


2

Я думаю , що код , який @daroczig надав може бути поліпшена шляхом заміни requireз libraryі обертання lapplyвиклику всередині invisible()функції. Отже, вдосконалений код буде виглядати наступним чином:

invisible(lapply(x, library, character.only = TRUE))

Цей код покращено, оскільки:

  1. library()як правило, перевагу над require()завантаженням пакетів, тому що перший видає помилку, якщо пакет не встановлений, а другий просто попереджає. Більше того, require()дзвінки library(), то чому б просто не скористатися library()безпосередньо!

    library("time")
    # Error in library("time") : there is no package called ‘time’
    
    require("time")
    # Loading required package: time
    # Warning message:
    # In library(package, lib.loc = lib.loc, character.only = TRUE, logical.return = TRUE,  :
    # there is no package called ‘time’
  2. Об'єкт списку повертається та друкується lapply() виклику, в цьому випадку не має сенсу, тому має сенс зробити висновок невидимим. Скажімо, ви використовуєте R Notebook для своєї роботи з аналізу, використання invisible()функції придушить вміст об'єкта списку і запобіжить захаращення у виведеному файлі ноутбука.


1

Невеликий мод відповіді Тайлера Рінкера, щоб додати чек для встановлення та завантаження Pacman:

#Install/load pacman
if(!require(pacman)){install.packages("pacman");require(pacman)}
#Install/load tons of packages
p_load(plyr,psych,tm)

Мені подобається рішення p_load, оскільки воно уникає цитування!

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.