Shiny学习笔记:响应式编程-1
简介
前面主要学习的是用户前段UI,现在开始将学习服务端,这是用户不可见的Shiny部分,Shiny服务端利用的是响应式编程(Reactive Programming
),这是一种优美的、强大的编程范式,但是也是容易让人迷惑的。Reactive Programming
的核心是指定从属关系,当输出变化时,所有与其相关的输出将自动变化。这使得Shiny App变得流畅。
server()函数
一个Shiny App的框架如下:
library(shiny)
ui <- fluidPage(
# front end interface
)
server <- function(input, output, session) {
# back end logic
}
shinyApp(ui, server)
UI相对来说是很简单的,所有用户看到都是同样的前端界面,但是server
端不一样,每个的用户都需要一份app
拷贝,不同用户之间互不干扰。
为了实现这种独立性,Shiny在每一个session
启动的时候会调用一次server()
函数。当server()
函数被调用的时候,会创建一个独立的本地环境,这可以保证每一个session
都有其独一无二的状态,可以隔离函数内部创建的变量,所以你会发现几乎所有的reactive programming
都是在server()
函数内部。
server()
函数有三个参数:input
、output
、session
。
Input
input
类似于一个list,包含用户在浏览器传递的数据,举个例子,如果UI含有一个数值输入count
:
ui <- fluidPage(
numericInput("count", label = "Number of values", value = 100)
)
那么你获取的数据就是input$count
,它的初始值为100, 当用户改变值的时候,input$count
值自动同步改变。input
是只读对象,如果在server()
函数内部修改input
会报错:
server <- function(input, output, session) {
input$count <- 10
}
shinyApp(ui, server)
#> Error: Attempted to assign value to a read-only reactivevalues object
input
会有选择性地允许谁可以读取它,要读取input
中的值,必须是由renderText()
,reactive()
等类似函数创建的reactive context
。
server <- function(input, output, session) {
message("The value of input$count is ", input$count)
}
shinyApp(ui, server)
#> Error: Operation not allowed without an active reactive context.
#> (You tried to do something that can only be done from inside
#> a reactive expression or observer.)
Output
与input
类似,区别是output
传递输出,input
接收输入。output
往往是与render
函数一起。
ui <- fluidPage(
textOutput("greeting")
)
server <- function(input, output, session) {
output$greeting <- renderText("Hello human!")
}
render
函数做两件事:
- 它指定了
output
与对应的input
- 将
R
代码转化为HTML