对data.frame有反应

时间:2020-07-30 15:51:42

标签: r shiny reactive dt

我正在努力处理反应性对象。我已经创建了一个反应性函数来更改data.frame,但是,我想在反应性函数之后计算一些度量。

到目前为止我的工作:

UI代码:

library(shiny)
library(DT)
ui <- fluidPage(
  # App title ----
  titlePanel("CheckList"),
  sidebarLayout(
    
    # Sidebar panel for inputs ----
    sidebarPanel(width = 2,
                 uiOutput("codePanel"), 
                 uiOutput("varPanel") 
    ),
    
    mainPanel(
      
      DT::dataTableOutput("text")
      
    )
  )
)

服务器代码:

server <- function(input, output) {
  
  df <- as.data.frame(cbind(matrix(round(runif(50, -1, 1), 3), 10), sample(0:1, 10, TRUE)))
  
  filt <- selectInput("codeInput",label ="filter1",
                      choices = as.list(unique(df$V6)), multiple = T, selected = 0)
  
  filt2 <- selectInput("varInput",label ="filter2",
                       choices = colnames(df[,-6]), multiple = T, selected = colnames(df[,-6]))
  
  output$codePanel <- renderUI({ filt
    
  })
  
  output$varPanel <- renderUI({ filt2
    
  })
  
  dat <- reactive({
    
    ab <- subset(df, V6 %in% input$codeInput) 
    ab <- ab[,-6]
    ab <- ab[, names(ab) %in% input$varInput] 
    
    
  })
  
 
  
  df1 <- as.data.frame(isolate(dat()))
  
  vals <- reactiveValues()
  vals$rm = mean(rowMeans(df1))
  vals$rr = range(df1)[2]-range(df1)[1]
  vals$r1 = abs(range(df1))[2] - mean(rowMeans(df1))
  vals$r0 = abs(range(df1))[1] - mean(rowMeans(df1))
  
}

我的问题是尝试isolate(dat()并将其转换为data.frame on:

  df1 <- as.data.frame(isolate(dat()))

错误消息显示“'closure'类型的对象不可子集化”。

1 个答案:

答案 0 :(得分:1)

我不知道此错误的原因(并且在运行您的代码时遇到另一个错误),但是服务器代码中存在几个问题。

input$codeInputinput$varInput在应用启动时为NULL,因此您必须使用req

  dat <- reactive({
    req(input$codeInput, input$varInput)
    ab <- subset(df, V6 %in% input$codeInput) 
    ab <- ab[,-6]
    ab <- ab[, names(ab) %in% input$varInput] 
  })

没有响应式上下文就无法调用dat(),就像编写df1 <- as.data.frame(dat())时一样。您可以按如下方式定义您的无功值vals

  vals <- reactiveValues()
  
  observe({
    vals$rm = mean(rowMeans(dat()))
    vals$rr = range(dat())[2]-range(dat())[1]
    vals$r1 = abs(range(dat()))[2] - mean(rowMeans(dat()))
    vals$r0 = abs(range(dat()))[1] - mean(rowMeans(dat()))
  })

请注意,我使用observe是因为它是一个反应性上下文,这是必需的。