How to Get Environment of a Variable in R

How can I make R read my environmental variables?

You want Sys.getenv() as in Sys.getenv("PATH"), say.

Or for your example, try

SIR <- Sys.getenv("SIR")   
system(paste("ec2-cancel-spot-instance-requests", SIR))

As for setting variables at startup, see help(Startup) to learn about ~/.Renvironment etc

How can I get an R environment via Sys.getenv() with GitHub Actions using secrets?

One solution that works, create ~/.Renviron within a block

- name: Create and populate .Renviron file
run: |
echo MY_SECRET="$MY_SECRET" >> ~/.Renviron
echo MY_SECRET2="$MY_SECRET2" >> ~/.Renviron
shell: bash

As long as this goes before your tests, this will work. It has been added to the github repo listed.

How to use the R environment and the globalenv() function

Your card deck is stored in a vector deck in your Global Environment.

deal <- function(){
card <- deck[1,]
assign("deck", deck[-1,], envir = globalenv())
card
}

Each function call creates it's own environment, an object assigned inside a function "lives" just inside of it. That's why you don't "see" a vector named card in your Global Environment (unless you created one before, but this vector is uneffected by deal functions card <- deck[1,] statement).

So assign("deck", deck[-1]) (without the envir argument) would be the same as

deal <- function(){
card <- deck[1,]
deck <- deck[-1,]
card
}

but this won't change your deck outside the function. The vector deck inside the function just exists inside the function. To change the deck outside the function, you have to tell R where to change it. So that's why assign("deck", deck[-1,], envir = globalenv()) is used.

So let's start over with your function deal:

card <- deck[1,]

assigns the first element of deck to card. But wait! deck doesn't exists inside the function? So how is this possible? If the object isn't found inside the function, R looks one level up, in your case most likely the Global Environment. So there R finds an object/vector named deck and does the assignment. Now we have an object/vector named card that exists inside the function.

For further understanding, take a look at Chapter 6: Functions in Advanced R.

R get object from global environment from function if object exists in global but use different default if not

You can modify your function to check if x exists in the .GlobalEnv and get it from there if it does, otherwise return the default value.

myfunc <- function(x = 30) {

if ("x" %in% ls(envir = .GlobalEnv)) {
get("x", envir = .GlobalEnv)
} else {
x
}

}

So if "x" %in% ls(envir = .GlobalEnv) is FALSE it would return

myfunc()
[1] 30

If x is found it would return it. if x <- 100:

myfunc()
[1] 100

Edit after comment

If you want to make sure to only return x from the global environment if x is not specified as an argument to myfunc, you can use missing(). It returns TRUE if x was not passed and FALSE if it was:

myfunc <- function(x = 30) {

if ("x" %in% ls(envir = .GlobalEnv) & missing(x)) {
get("x", envir = .GlobalEnv)
} else {
x
}

}

So for your example:

x <- 100
myfunc(x=300)
[1] 300

Accessing environment variables set in R session from shell

The environmental variable dies with the process.

Each process has its own set of environmental variables, inherited from the parent process. When you create the environmental variable BLAH, you create it in the environment of the R process you're running, but not in the environment of the parent process.

If you want another process to access this environmental variable, you'll need to start the process from within R. Then the child process will inherit BLAH. This documentation for Sys.setenv mentions this:

Sys.setenv sets environment variables (for other processes called from within R or future calls to Sys.getenv from this R process).

For example:

Sys.setenv(BLAH="blah")
system("echo $BLAH")
# blah

How do I correctly use the env variable for data.tables within a function

It's because dots isn't a call, it's a list of calls. So when data.table evaluates j it's trying to insert that list into a new column.

To fix this you need to splice the list of calls into a single call. You can do this in a call to ':='() directly (Option 1 below), but you can also break this into multiple steps that mirrors what you were doing above by converting dots to be a call to list() (Option 2).

library(data.table)

data <- data.table::data.table(a = 1:5, b = 2:6)

# Option 1 - call to ':='
test <- function(data, ...) {
dots <- eval(substitute(alist(...)))
j <- bquote(':='(..(dots)), splice = TRUE)
print(j)
data[, j, env = list(j = j)][]
}

# # Option 2 - convert dots to a call to a list
# test <- function(data, ...) {
# dots <- eval(substitute(alist(...)))
# dots_names <- names(dots)
# dots <- bquote(list(..(unname(dots))), splice = TRUE)
# j <- call(":=", dots_names, dots)
# print(j)
# data[, j, env = list(j = j)][]
# }

test(data = data, c = a + 1, double_b = b * 2)
#> `:=`(c = a + 1, double_b = b * 2)
#> a b c double_b
#> <int> <int> <num> <num>
#> 1: 1 2 2 4
#> 2: 2 3 3 6
#> 3: 3 4 4 8
#> 4: 4 5 5 10
#> 5: 5 6 6 12

Edit: You can also use test2() if you want to be able to edit the same column or use newly made columns.

test2 <- function(data, ...) {
dots <- eval(substitute(alist(...)))
dots_names <- names(dots)
for (i in seq_along(dots)) {
dot_name <- dots_names[[i]]
dot <- dots[[i]]
j <- call(":=", dot_name, dot)
print(j)
data[, j, env = list(j = j)]
}
data[]
}


Related Topics



Leave a reply



Submit