R shiny reactive return more than one object - r

I am making use of the example provided in in the answer to this question: Shiny Reactivity
They make use of two return statements in the reactive function. I believe return(x) is just a mistake. However, I am wondering if I can return more than one object with one reactive statement?

You can think of reactive() as any regular function that returns a value, it just happens to return a reactive value and to always be called automatically when needed. In a regular function, how do you return more than one object? You can return a list, for example. You can do the same with reactive().

Related

Upload a .xlsx file to Shiny and load in all the tabs as a list [duplicate]

I have a shiny app and when I run it I get an error saying that an object of type ‘closure’ is not subsettable. What is that and how can I fix it?
Note: I wrote this question as this comes up a lot, and the possible dupes are either not shiny related or so specific that it is not obvious that the answers are broadly applicable.
See also this question which covers this error in a non-Shiny context.
How to fix this:
This is a very common error in shiny apps. This most typically appears when you create an object such as a list, data.frame or vector using the reactive() function – that is, your object reacts to some kind of input. If you do this, when you refer to your object afterwards, you must include parentheses.
For example, let’s say you make a reactive data.frame like so:
MyDF<-reactive({ code that makes a data.frame with a column called “X” })
If you then wish to refer to the data.frame and you call it MyDF or MyDF$X you will get the error. Instead it should be MyDF() or MyDF()$X You need to use this naming convention with any object you create using reactive().
Why this happens:
When you make a reactive object, such as a data.frame, using reactive() it is tempting to think of it as just like any other non-reactive data.frame and write your code accordingly. However, what you have created is not really a data.frame. Rather, what you have made is instructions, in the form of a function, which tell shiny how to make the data.frame when it is needed. When you wish to actually use this function to get the data.frame you have to use the parenthesis, just like you would any other function in R. If you forget to use the parenthesis, R thinks you are trying to use part of a function and gives you the error. Try typing:
plot$x
at the command line and you will get the same error.
You may not see this error right when your app starts. Reactive objects have what is called “lazy” evaluation. They are not evaluated until they are needed for some output. So if your data.frame is only used to make a plot, the data.frame will not exist until the user sees the plot for the first time. If when the app starts up the user is required to click a button or change tabs to see the plot, the code for the data.frame will not be evaluated until that happens. Once that happens, then and only then will shiny use the current values of the inputs to run the function that constructs the data.frame needed to make the plot. If you have forgotten to use the parentheses, this is when shiny will give you the error. Note that if the inputs change, but the user is not looking at the plot, the function that makes the data.frame will not be re-run until the user looks at the plot again.

Is it possible to make a R Shiny reactive function that accepts arguments like a normal function?

I have a situation where I have a reactive function that I would like to be used in several different plots, but to be calling/checking different parts of a dataframe stored as reactiveValues.
If I had a normal function I could call it and pass it an argument to index a specific column of the reactive values e.g.,:
my_function <- function(column) {what the function does}
Then when calling the function:
my_function(column = 3)
But for a reactive function I don't see how I can do something like this.
my_function <- reactive({what the function does})
At the moment, I can just make multiple versions of essentially the same function that call different indexes but that is a lot of extra lines of code as the function is quite long.
The situation is also not one where I see a simple way of using another reactive value that can be called inside the reactive function that would appropriately call the right column index in all cases.
Is there a way to define the reactive function so that when it is called, I can pass it an argument?

R shiny ERROR: object of type 'closure' is not subsettable [duplicate2] [duplicate]

I have a shiny app and when I run it I get an error saying that an object of type ‘closure’ is not subsettable. What is that and how can I fix it?
Note: I wrote this question as this comes up a lot, and the possible dupes are either not shiny related or so specific that it is not obvious that the answers are broadly applicable.
See also this question which covers this error in a non-Shiny context.
How to fix this:
This is a very common error in shiny apps. This most typically appears when you create an object such as a list, data.frame or vector using the reactive() function – that is, your object reacts to some kind of input. If you do this, when you refer to your object afterwards, you must include parentheses.
For example, let’s say you make a reactive data.frame like so:
MyDF<-reactive({ code that makes a data.frame with a column called “X” })
If you then wish to refer to the data.frame and you call it MyDF or MyDF$X you will get the error. Instead it should be MyDF() or MyDF()$X You need to use this naming convention with any object you create using reactive().
Why this happens:
When you make a reactive object, such as a data.frame, using reactive() it is tempting to think of it as just like any other non-reactive data.frame and write your code accordingly. However, what you have created is not really a data.frame. Rather, what you have made is instructions, in the form of a function, which tell shiny how to make the data.frame when it is needed. When you wish to actually use this function to get the data.frame you have to use the parenthesis, just like you would any other function in R. If you forget to use the parenthesis, R thinks you are trying to use part of a function and gives you the error. Try typing:
plot$x
at the command line and you will get the same error.
You may not see this error right when your app starts. Reactive objects have what is called “lazy” evaluation. They are not evaluated until they are needed for some output. So if your data.frame is only used to make a plot, the data.frame will not exist until the user sees the plot for the first time. If when the app starts up the user is required to click a button or change tabs to see the plot, the code for the data.frame will not be evaluated until that happens. Once that happens, then and only then will shiny use the current values of the inputs to run the function that constructs the data.frame needed to make the plot. If you have forgotten to use the parentheses, this is when shiny will give you the error. Note that if the inputs change, but the user is not looking at the plot, the function that makes the data.frame will not be re-run until the user looks at the plot again.

How do I remove an object from within a function environment in R?

How do I remove an object from the current function environment?
I'm trying to achieve this:
foo <- function(bar){
x <- bar
rm(bar, envir = environment())
print(c(x, is.null(bar)))
}
Because I want the function to be able to handle multiple inputs.
Specifically I'm trying to pass either a dataframe or a vector to the function, and if I'm passing a dataframe I want to set the vector to NULL for later error handling.
If you want, you can watch my DepthPlotter script, where I want to let the second function check if depth is a dataframe, and if so, assign it to df in stead and remove depth from the environment.
Here is a very brief sketch of how to set this up using S3 method dispatch.
First, you define your generic:
DepthPlotter <- function(depth,...){
UseMethod("DepthPlotter", depth)
}
Then you define methods for specific classes of the argument depth. As a very basic example in your case, you might create only two, a data.frame method and a default method to handle the vector case:
DepthPlotter.default <- function(depth, variable, ...){
#Here you write a function assuming that depth is
# anything but a data frame
}
DepthPlotter.data.frame <- function(depth,...){
#Here you'd write a function that assumes
# that depth is a data frame
}
And then you can call DepthPlotter() using either type of argument and the correct function will be run based upon the result of class(depth).
The example I've sketched out here is a little crude, since I've used a default method to handle the vector case. You could write .numeric and .integer methods to handle numeric or integer vectors more specifically. In my example, the .default method will be called for any case other than data.frame, so if you go this route you'd want to write some code in there that checks for strange cases like depth being a complicated list, or other odd object, if you think there's a chance something like that might be passed to the function.

R- accessing varibales created within a user defined function after end of function

Take a basic function
fun<-function(){
x<-c(1,2,3,4,5)
y<-c(1,2,3,4,5)
t<-x+y
return(t)
}
After I have run the function, is there a way I can access any of the variables created within the function. Either by specifying the variable- something like this:
fun$y
or
fun$t
or is there some way of asking R to save the variable within the function for use during my current R session (I'm not looking to save it permanently). AKA something along the lines of:
fun<-function(){
x<-c(1,2,3,4,5)
y<-c(1,2,3,4,5)
t<-x+y
Y<-save y for latter use
T<-save T for latter use
return(t)
}
Thanks!
You can't use a variable outside of its scope.
What you can do is use a list to return multiple values from your function.
Here's a good example.
Yes and no.
Yes, it is technically possible to make assignments to variables outside the scope of your function, so that they are accessible elsewhere. Typically this is done using either <<-, which assigns in the global environment if the variable being assigned can't be found, or calling assign and specifying an environment directly.
But...
No, you should probably not be doing this. R is a functional language, which means that it is intended to be used such that its functions do not create side-effects. If you violate this principle too much, you will inevitably run afoul of serious problems that will be difficult, if not impossible to debug.
If you create variables within a function that you will need later, it is considered best practice to return them all in a list, as Benito describes.

Resources