我有一個R腳本與不同計算機上的多個用戶共享。其中一行包含install.packages("xtable")
命令。在運行install.packages()前檢查已安裝的軟件包()
問題是,每次有人運行腳本時,R花費大量時間顯然重新安裝軟件包(實際上它需要一些時間,因爲真正的案例有幾個軟件包的向量)。
如何首先檢查軟件包是否已安裝,然後只運行install.packages()
而不是?
我有一個R腳本與不同計算機上的多個用戶共享。其中一行包含install.packages("xtable")
命令。在運行install.packages()前檢查已安裝的軟件包()
問題是,每次有人運行腳本時,R花費大量時間顯然重新安裝軟件包(實際上它需要一些時間,因爲真正的案例有幾個軟件包的向量)。
如何首先檢查軟件包是否已安裝,然後只運行install.packages()
而不是?
嘗試:或"xtable" %in% rownames(installed.packages())
等'if(「xtable」%in%rownames(installed.packages())== FALSE){install.packages(「xtable」)}' – Henry 2012-02-18 14:02:23
我用'if(!pacote%in%installed .packages())install.packages(pacote)'。這很好,很優雅,謝謝! – 2012-02-19 14:40:11
InsPack < - function(pack){ if(!pack%in%installed。包()){ 打印 (粘貼( 「安裝」,包)) install.packages(包) } 其他打印(粘貼(包 「已安裝」)) } – Faridcher 2015-09-08 18:25:42
爲什麼不直接從腳本中刪除該行?如果最終用戶不具有的智慧安裝xtable
根據需要,你有更大的問題:-( 這就是說,看看installed.packages()
編輯:!一分鐘宕,Ninja'd
編輯:一般建議:加載包sos
,你會發現它很容易得到答案了不少「有,做XXXXX功能」的問題
好吧,誰是weisenheimer通過3歲的帖子抨擊只是爲了downvote的東西? – 2015-04-30 12:24:47
這是一個函數I經典EN用於檢查一個包,否則安裝它,然後重新裝入:
pkgTest <- function(x)
{
if (!require(x,character.only = TRUE))
{
install.packages(x,dep=TRUE)
if(!require(x,character.only = TRUE)) stop("Package not found")
}
}
作品像pkgTest("xtable")
。它只適用於鏡像設置,但您可以在require
調用中輸入。
或者選擇在回購install.packages調用例如'install.packages(x,dep = TRUErepos ='http:// star-www.st-andrews.ac.uk/cran /'') – moadeep 2013-03-01 10:36:56
這應該這樣做。如果您需要檢查多個,則可以將required.packages
作爲向量。
required.packages <- "data.table"
new.packages <- required.packages[!(required.packages %in% installed.packages()[,"Package"])]
if(length(new.packages)) install.packages(new.packages)
我使用薩沙Epskamp和曙光的輸入得到的溶液。這裏的功能:
instalaPacotes <- function(pacote) {
if (!pacote %in% installed.packages()) install.packages(pacote)
}
它的工作原理默默地,呼應咱這包「包中」已經安裝否則安裝。不要忘記在引號之間寫下包裹的名字!
如果我爲'else添加庫(x) '在你的'if'函數中出現錯誤。有什麼建議麼? – 2015-03-25 14:57:35
@ timothy.s.lau:你得到什麼錯誤?你的條件寫得如何? – 2015-03-25 18:31:36
# Function to check whether package is installed
is.installed <- function(mypkg){
is.element(mypkg, installed.packages()[,1])
}
# check if package "hydroGOF" is installed
if (!is.installed("hydroGOF")){
install.packages("hydroGOF")
}
試試這個怎麼樣?
#will install the pROC library if you don't have it
if(!is.element('pROC', installed.packages()[,1]))
{install.packages('pROC')
}else {print("pROC library already installed")}
Or a massively overticked example from drknexus/repsych
on github, glibrary。幾乎肯定有更高效和更好的方法來做到這一點,但我很久以前編程它,它基本上工作。
例如:glibrary(xtable,sos,data.table)
但我不認爲如果你打電話glibrary("xtable","sos","data.table")
來代替它,它會嚇壞了。推/拉/叉歡迎。
代碼的功能:
#' Try to load a library, if that fails, install it, then load it.
#'
#' glibrary short for (get)library.
#' The primary aim of this function is to make loading packages more transparent. Given that we know we want to load a given package, actually fetching it is a formality. glibrary skims past this formality to install the requested package.
#'
#' @export
#' @param ... comma seperated package names
#' @param lib.loc See \code{\link{require}}
#' @param quietly See \code{\link{require}}
#' @param warn.conflicts See \code{\link{require}}
#' @param pickmirror If TRUE, glibrary allows the user to select the mirror, otherwise it auto-selects on the basis of the country code
#' @param countrycode This option is ignored and the first mirror with the substring "Cloud", e.g. the RStudio cloud, is selected. If no mirrors with that substring are identified, glibrary compares this value to results from getCRANmirrors() to select a mirror in the specified country.
#' @return logical; TRUE if glibrary was a success, an error if a package failed to load
#' @note keep.source was an arguement to require that was deprecated in R 2.15
#' @note This warning \code{Warning in install.packages: InternetOpenUrl failed: 'The operation timed out'} indicates that the randomly selected repository is not available. Check your internet connection. If your internet connection is fine, set pickmirror=TRUE and manually select an operational mirror.
#' @examples
#' #glibrary(lattice,MASS) #not run to prevent needless dependency
glibrary <- function(..., lib.loc = NULL, quietly = FALSE, warn.conflicts = TRUE, pickmirror = FALSE, countrycode = "us") {
warningHandle <- function(w) {
if (grepl("there is no package called",w$message,fixed=TRUE)) {
return(FALSE) #not-loadable
} else {
return(TRUE) #loadable
}
}
character.only <- TRUE #this value is locked to TRUE so that the function passes the character value to require and not the variable name thislib
librarynames <- unlist(lapply(as.list(substitute(.(...)))[-1],as.character))
#if package already loaded, remove it from librarynames before processing further
si.res <- sessionInfo()
cur.loaded <- c(si.res$basePkgs,names(si.res$otherPkgs)) #removed names(si.res$loadedOnly) because those are loaded, but not attached, so glibrary does need to handle them.
librarynames <- librarynames[librarynames %!in% cur.loaded]
success <- vector("logical", length(librarynames))
if (length(success)==0) {return(invisible(TRUE))} #everything already loaded, end.
alreadyInstalled <- installed.packages()[,"Package"]
needToInstall <- !librarynames %in% alreadyInstalled
if (any(needToInstall)) {
if (pickmirror) {chooseCRANmirror()}
if (getOption("repos")[["CRAN"]] == "@[email protected]") {
#Select the first "Cloud" if available
m <- getCRANmirrors(all = FALSE, local.only = FALSE)
URL <- m[grepl("Cloud",m$Name),"URL"][1] #get the first repos with "cloud" in the name
if (is.na(URL)) { #if we did not find the cloud,
#Fall back and use the previous method
message("\nIn repsych:glibrary: Now randomly selecting a CRAN mirror. You may reselect your CRAN mirror with chooseCRANmirror().\n")
#if there is no repository set pick a random one by country code
getCRANmirrors.res <- getCRANmirrors()
foundone <- FALSE #have we found a CRAN mirror yet?
#is it a valid country code?
if (!countrycode %in% getCRANmirrors.res$CountryCode) {
stop("In repsych::glibrary: Invalid countrycode argument")
}
ticker <- 0
while (!foundone) {
ticker <- ticker + 1
URL <- getCRANmirrors.res$URL[sample(grep(countrycode, getCRANmirrors.res$CountryCode), 1)]
host.list <- strsplit(URL, "/")
host.clean <- unlist(lapply(host.list, FUN = function(x) {return(x[3])}))
#make sure we can actually access the package list
if (nrow(available.packages(contrib.url(URL)))!=0) {foundone <- TRUE}
if (ticker > 5) {stop("In repsych::glibrary: Unable to access valid repository. Is the internet connection working?")}
} #end while
} #end else
repos <- getOption("repos")
repos["CRAN"] <- gsub("/$", "", URL[1L])
options(repos = repos)
} #done setting CRAN mirror
#installing packages
installResults <- sapply(librarynames[needToInstall],install.packages)
#checking for successful install
needToInstall <- !librarynames %in% installed.packages()[,"Package"]
if (any(needToInstall)) {
stop(paste("In repsych::glibrary: Could not download and/or install: ",paste(librarynames[needToInstall],collapse=", "),"... glibrary stopped.",sep=""))
} # done reporting any failure to install
} #done if any needed to install
#message("In repsych::glibrary: Attempting to load requested packages...\n")
#success <- tryCatch(
success <- sapply(librarynames,require, lib.loc = lib.loc, quietly = FALSE, warn.conflicts = warn.conflicts, character.only = TRUE)
#, warning=warningHandle) #end tryCatch
if(length(success) != length(librarynames)) {stop("A package failed to return a success in glibrary.")}
if (all(success)) {
#message("In repsych::glibrary: Success!")
return(invisible(TRUE))
} else {
stop(paste("\nIn repsych::glibrary, unable to load: ", paste(librarynames[!success]),
collapse = " "))
}
stop("A problem occured in glibrary") #shouldn't get this far down, all returns should be made.
}
NULL
鏈接已損壞。這正是爲什麼StackOverflow不允許鏈接唯一的答案... – 2015-10-06 06:17:22
@MilesErickson我沒有想到任何人會希望在帖子中的這麼多的代碼。和許多代碼只回答得到不贊成R隨着包提前,所以鏈接到一個github存儲庫(仍然存在)對我來說是有道理的。無論如何,鏈接固定和代碼添加。 – russellpierce 2015-10-06 06:23:09
我發現了一個packages
腳本的地方,我總是把每一個腳本加載我的圖書館。它會執行所有庫處理(下載,安裝和加載),並且只在需要時才執行。
# Install function for packages
packages<-function(x){
x<-as.character(match.call()[[2]])
if (!require(x,character.only=TRUE)){
install.packages(pkgs=x,repos="http://cran.r-project.org")
require(x,character.only=TRUE)
}
}
packages(ggplot2)
packages(reshape2)
packages(plyr)
# etc etc
讀了大家的回答,我在這裏和那裏提了一些提示並創建了我的。其實非常類似於大多數。
## These codes are used for installing packages
# function for installing needed packages
installpkg <- function(x){
if(x %in% rownames(installed.packages())==FALSE) {
if(x %in% rownames(available.packages())==FALSE) {
paste(x,"is not a valid package - please check again...")
} else {
install.packages(x)
}
} else {
paste(x,"package already installed...")
}
}
# install necessary packages
required_packages <- c("sqldf","car")
lapply(required_packages,installpkg)
如果你想簡單地做越好:
packages <- c("ggplot2", "dplyr", "Hmisc", "lme4", "arm", "lattice", "lavaan")
if (length(setdiff(packages, rownames(installed.packages()))) > 0) {
install.packages(setdiff(packages, rownames(installed.packages())))
}
替換那些需要在第一行列出的軟件包來運行你的代碼,瞧!
我喜歡這種方法。當'packages'中的所有軟件包已經安裝時,這是一種恥辱。 – jbaums 2014-06-04 02:00:34
不錯,我已經更新了代碼以避免這種情況,儘管我不想失去雙線方法的簡單性。也許別人可以想到一個更清潔的解決方案。 – 2014-06-04 02:04:03
看着我的舊功能,使用上面的提示更新它,這就是我得到的。
# VERSION 1.0
assign("installP", function(pckgs){
ins <- function(pckg, mc){
add <- paste(c(" ", rep("-", mc+1-nchar(pckg)), " "), collapse = "");
if(!require(pckg,character.only=TRUE)){
reps <- c("http://lib.stat.cmu.edu/R/CRAN","http://cran.uk.R-project.org");
for (r in reps) try(utils::install.packages(pckg, repos=r), silent=TRUE);
if(!require(pckg,character.only = TRUE)){ cat("Package: ",pckg,add,"not found.\n",sep="");
}else{ cat("Package: ",pckg,add,"installed.\n",sep="");}
}else{ cat("Package: ",pckg,add,"is loaded.\n",sep=""); } }
invisible(suppressMessages(suppressWarnings(lapply(pckgs,ins, mc=max(nchar(pckgs)))))); cat("\n");
}, envir=as.environment("dg_base"))
installP(c("base","a","TFX"))
Package: base ------------------- is loaded.
Package: a ---------------------- not found.
Package: TFX -------------------- installed.
我已經實現了安裝和靜默加載所需R包的函數。希望可能有幫助。下面是代碼:
# Function to Install and Load R Packages
Install_And_Load <- function(Required_Packages)
{
Remaining_Packages <- Required_Packages[!(Required_Packages %in% installed.packages()[,"Package"])];
if(length(Remaining_Packages))
{
install.packages(Remaining_Packages);
}
for(package_name in Required_Packages)
{
library(package_name,character.only=TRUE,quietly=TRUE);
}
}
# Specify the list of required packages to be installed and load
Required_Packages=c("ggplot2", "Rcpp");
# Call the Function
Install_And_Load(Required_Packages);
另外還有CRAN包pacman它具有p_load
功能來安裝一個或多個包(但僅在必要時),然後加載它們。
我建議使用system.file
更輕量級的解決方案。
is_inst <- function(pkg) {
nzchar(system.file(package = pkg))
}
is_inst2 <- function(pkg) {
pkg %in% rownames(installed.packages())
}
library(microbenchmark)
microbenchmark(is_inst("aaa"), is_inst2("aaa"))
## Unit: microseconds
## expr min lq mean median uq max neval
## is_inst("aaa") 22.284 24.6335 42.84806 34.6815 47.566 252.568 100
## is_inst2("aaa") 1099.334 1220.5510 1778.57019 1401.5095 1829.973 17653.148 100
microbenchmark(is_inst("ggplot2"), is_inst2("ggplot2"))
## Unit: microseconds
## expr min lq mean median uq max neval
## is_inst("ggplot2") 336.845 386.660 459.243 431.710 483.474 867.637 100
## is_inst2("ggplot2") 1144.613 1276.847 1507.355 1410.054 1656.557 2747.508 100
requiredPackages = c('plyr','ggplot2','ggtern')
for(p in requiredPackages){
if(!require(p,character.only = TRUE)) install.packages(p)
library(p,character.only = TRUE)
}
使用'require'(例如@ SachaEpskamp的解決方案)是要走的路。使用'rownames(installed.packages())'的方法很慢並且不總是可靠的(參見'find.package'的細節和'installed.packages'的提示)。 'require'確保軟件包不僅可以安裝,而且可以使用(即滿足依賴關係等)。 – jbaums 2014-06-04 02:22:32