Элегантный способ проверить отсутствующие пакеты и установить их? - PullRequest
288 голосов
/ 03 ноября 2010

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

Существует ли элегантный способ вызова installed.packages(), сравните его с теми, которые я загружаю и устанавливаю в случае отсутствия?

Ответы [ 26 ]

1 голос
/ 22 июня 2017
source("https://bioconductor.org/biocLite.R")
if (!require("ggsci")) biocLite("ggsci")
1 голос
/ 02 декабря 2012

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

p<-c('ggplot2','Rcpp')
install_package<-function(pack)
{if(!(pack %in% row.names(installed.packages())))
{
  update.packages(ask=F)
  install.packages(pack,dependencies=T)
}
 require(pack,character.only=TRUE)
}
for(pack in p) {install_package(pack)}

completeFun <- function(data, desiredCols) {
  completeVec <- complete.cases(data[, desiredCols])
  return(data[completeVec, ])
}
1 голос
/ 26 августа 2016
library <- function(x){
  x = toString(substitute(x))
if(!require(x,character.only=TRUE)){
  install.packages(x)
  base::library(x,character.only=TRUE)
}}

Это работает с именами пакетов без кавычек и довольно элегантно (см. Ответ GeoObserver)

1 голос
/ 07 ноября 2015
 48 lapply_install_and_load <- function (package1, ...)
 49 {
 50     #
 51     # convert arguments to vector
 52     #
 53     packages <- c(package1, ...)
 54     #
 55     # check if loaded and installed
 56     #
 57     loaded        <- packages %in% (.packages())
 58     names(loaded) <- packages
 59     #
 60     installed        <- packages %in% rownames(installed.packages())
 61     names(installed) <- packages
 62     #
 63     # start loop to determine if each package is installed
 64     #
 65     load_it <- function (p, loaded, installed)
 66     {
 67         if (loaded[p])
 68         {
 69             print(paste(p, "loaded"))
 70         }
 71         else
 72         {
 73             print(paste(p, "not loaded"))
 74             if (installed[p])
 75             {
 76                 print(paste(p, "installed"))
 77                 do.call("library", list(p))
 78             }
 79             else
 80             {
 81                 print(paste(p, "not installed"))
 82                 install.packages(p)
 83                 do.call("library", list(p))
 84             }
 85         }
 86     }
 87     #
 88     lapply(packages, load_it, loaded, installed)
 89 }
1 голос
/ 12 июня 2015

Вот мой код для этого:

packages <- c("dplyr", "gridBase", "gridExtra")
package_loader <- function(x){
    for (i in 1:length(x)){
        if (!identical((x[i], installed.packages()[x[i],1])){
            install.packages(x[i], dep = TRUE)
        } else {
            require(x[i], character.only = TRUE)
        }
    }
}
package_loader(packages)
0 голосов
/ 20 декабря 2017

В моем случае я хотел один лайнер, который мог бы запускаться из командной строки (фактически через Makefile).Вот пример установки «VGAM» и «пера», если они еще не установлены:

R -e 'for (p in c("VGAM", "feather")) if (!require(p, character.only=TRUE)) install.packages(p, repos="http://cran.us.r-project.org")'

Изнутри R это будет просто:

for (p in c("VGAM", "feather")) if (!require(p, character.only=TRUE)) install.packages(p, repos="http://cran.us.r-project.org")

Здесь ничего нетпредыдущие решения, за исключением того, что:

  • Я держу его в одной строке
  • Я жестко кодирую параметр repos (чтобы избежать всплывающих окон, спрашивающихиспользуемое зеркало)
  • Я не удосужился определить функцию, которая будет использоваться в другом месте

Также обратите внимание на важное значение character.only=TRUE (без него require попытается загрузить пакет p).

...