R Shiny:如何在执行反应语句之前更新输入对象

2024-01-12

我正在基于很棒的 R Shiny 包构建一个探索性视觉应用程序。该应用程序要做的一件事是读取实值“测量”列并显示这些测量值的箱线图。此外,还有一个可选的selectInput小部件,允许用户选择group要深入研究的变量。这group变量基本上包含具有分类值的列的名称,例如性别(女性与男性)、国家/地区(美国、加拿大等)。因此,如果从以下选项中选择“性别”group selectInput,应用程序将显示两个箱线图,一个用于女性,另一个用于男性。

为了让用户能够灵活地关注某些类别(例如仅女性),我想出了checkboxGroupInput仅在以下情况下显示group变量同时被选择choices and selected最初设置为所有类别group多变的。例如,当用户只想查看女性的箱线图时,他/她可以轻松取消选中男性的复选框,并且男性的箱线图被删除,而女性的箱线图保留。

下列的暖流 https://stackoverflow.com/users/4190526/warmoverflow的建议,这是一个可复制的玩具示例

# global setup
library(shiny)
library(ggplot2)
library(dplyr)
set.seed(12345)
dummy_data <- data.frame(
    Value = c(rnorm(50), 2 + rnorm(50)),
    Gender = c(rep('Female', 50), rep('Male', 50)),
    Country = c(rep('US', 50), rep('CA', 50)),
    stringsAsFactors = FALSE
)

# ui function
ui <- fluidPage(
    sidebarLayout(
        sidebarPanel(
            selectInput('group', 'Group',
                        c('Choose'='', setdiff(names(dummy_data), 'Value'))),
            uiOutput('group_select')
        ),
        mainPanel(plotOutput('box_plot'))
    )
)

# server function
server <- function(input, output) {

    # the group level select/unselect widget
    output$group_select <- renderUI({
        req(input$group)
        data <- dummy_data
        group_levels <- unique(data[[input$group]])
        conditionalPanel(
            condition = "input.group != ''",
            checkboxGroupInput('group_select', input$group,
                               choices = group_levels, selected = group_levels)
        )
    })

    # filter the data if group variable is selected
    data_to_plot <- reactive({
        data <- dummy_data
        if(!(is.null(input$group) || input$group == '')) {
            data <- data %>% 
                mutate_(group_ = input$group) %>%
                filter(group_ %in% input$group_select)
        } else {
            data$group_ <- as.factor(rep.int(1, nrow(data)))
        }
        return(data)
    })

    # show the boxplot
    output$box_plot <- renderPlot({
        data <- data_to_plot()
        validate(
            need(!(is.null(data) || nrow(data) == 0),
                 'There are no data to plot!')
        )
        ggplot(data = data, aes(factor(group_), Value)) + geom_boxplot()
    })
}

shinyApp(ui = ui, server = server)

嗯,代码可以工作,但是reactive语句不必要地运行两次,一次当input$group更新后还有另一个input$group_select得到更新,因为您可以注意到错误消息“没有要绘制的数据!”当您从选项中选择“性别”时group下拉列表。所以我的问题是:有没有办法保证以下执行顺序:

  1. input$group已更新->
  2. input$group_select已更新 ->
  3. reactive更新后(重新)执行input$group and input$group_select

我花了几乎一整天的时间寻找解决方案但收效甚微。

  • 罗杰戴似乎已经解决了这个问题使用 sendInputMessage 和 receiveMessage 使闪亮的输入对象具有反应性 https://groups.google.com/forum/#!topic/shiny-discuss/udPfQ9o8JVY。但他的方法涉及创建一个 jstree,这对我来说完全是一个陌生的领域,看起来他已经从他的 Github 上删除了该解决方案。
  • 另一个可能的线索是使用observeEvent此处描述(R闪亮观察运行在加载UI之前,这会导致空参数 https://stackoverflow.com/questions/22845874/r-shiny-observe-running-before-loading-of-ui-and-this-causes-null-parameters)。然而,observeEvent当您取消选择一个或多个类别时忽略它input$group_select.

Roger Day 指出,其困难在于输入更新函数通常不是反应性的,因此(根据我的实验和理解)比反应性语句执行得晚。或者,如果有一种方法可以使输入更新功能反应,则可以应用优先级值以所需的方式改变执行顺序。

任何意见都将不胜感激!抱歉描述太长!


我想我已经找到了解决方案。文中提到的方向未命名用户 https://stackoverflow.com/users/4956364/unnameduser and 暖流 https://stackoverflow.com/users/4190526/warmoverflow是对的。总体想法是创建一个反应值来表示,或更准确地说是监控group用户选择的类别并检测两者的任何变化group变量(使用observe) and group变量选择的类别(使用observe),然后通过在中添加以下代码块来相应地修改无功值server功能。

# use a reactive value to represent group level selection
group_selects <- reactiveValues(value = NULL)
observe({
    input$group
    if(is.null(input$group) || input$group == '')
        group_selects$value <- NULL
    else {
        data <- dummy_data
        group_selects$value <- unique(data[[input$group]])
    }
})
observe({
    input$group_select
    group_selects$value <- input$group_select
})

然后使用group_selects$value来代替input$group_select在数据操作块中

# filter the data if group variable is selected
data_to_plot <- reactive({
    data <- dummy_data
    if(!(is.null(input$group) || input$group == '')) {
        req(group_selects$value)                        # To prevent unnecessary re-run
        data <- data %>% 
            mutate_(group_ = input$group) %>%
            filter(group_ %in% group_selects$value)     # Replaced input$group_select
    } else {
        data$group_ <- as.factor(rep.int(1, nrow(data)))
    }
    return(data)
})
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

R Shiny:如何在执行反应语句之前更新输入对象 的相关文章

  • 从日期变量创建月末日期

    我有一个包含日期变量的大型数据框 它反映了该月的第一天 有没有一种简单的方法来创建代表该月最后一天的新数据框日期变量 以下是一些示例数据 date start month seq as Date 2012 01 01 length 4 by
  • rpart“as.character(x) 中的错误:无法强制类型 'builtin' 为类型 'character' 的向量”消息是什么意思?

    我一直在用头撞rpart几天了 尝试为我拥有的这个数据集制作分类树 我认为现在是时候询问生命线了 我确信这是我没有看到的愚蠢的事情 但这里是我一直在做什么 EuropeWater lt read csv file paste Users a
  • 如何对数字进行四舍五入并使其显示零?

    R 中将数字四舍五入到小数点后 2 位的常用代码是 gt a 14 1234 gt round a digits 2 gt a gt 14 12 但是 如果该数字的前两位小数位为零 则 R 会在显示中抑制零 gt a 14 0034 gt
  • 尝试使用 JRI 将 R 与我的 Java 应用程序集成,但出现错误。谁能解释一下原因和解决办法吗?

    我需要将 Java 与 R 集成来运行一些数学命令并使用 R 的功能进行绘图 以下部分代码给出了错误 public static void main String args HelloRWorld r new HelloRWorld r h
  • Quantmod 的简单功能不再起作用

    我明天要交论文 我收到了一条关于 quantmod 的非常奇怪的错误消息 这是我在过去几周使用这个包时从未遇到过的 我无法导入特定于道琼斯指数 DJI 的数据 我收到以下错误消息 getSymbols DJI src yahoo from
  • 列出 R 数据文件的内容而不加载

    我有时用print load myDataFile RData 当我加载数据文件时列出它的内容 有没有办法列出内容而不加载数据文件中包含的对象 我认为如果不加载对象就无法做到这一点 解决方案可能是使用包装器将 R 对象保存到save 该函数
  • 需要在R中按行绑定列表数据

    我在 R 中按行绑定列表时遇到问题 我的列表数据集是 id 1 data k 1 id k b c 1 1 1 3 data k 2 id k b c 1 2 1 4 id 2 data k 1 id k b c 2 1 1 6 data
  • 如何在 data.table 中分组后使用条件计算行数

    我有以下数据框 dat lt read csv s1 s2 v1 v2 a b 10 20 a b 22 NA a b 13 33 c d 3 NA c d 4 5 NA c d 10 20 dat gt A tibble 6 x 4 gt
  • 实现 XGboost 自定义目标函数

    我正在尝试使用 XGboost 实现自定义目标函数 在 R 中 但我也使用 python 所以有关 python 的任何反馈也很好 我创建了一个返回梯度和粗麻布的函数 它工作正常 但是当我尝试运行 xgb train 时它不起作用 然后 我
  • picker输入字体或背景颜色

    我在闪亮的仪表板中使用 pickerInput 这很好 除了一个问题 背景颜色和字体颜色太相似 使得过滤器选择难以阅读 有什么办法可以改变背景或字体颜色吗 如果可能的话 我想继续使用 pickerInput 但如果有一个带有 selectI
  • 如何在 R 中执行近似(模糊)名称匹配

    我有一个专门用于生物学期刊的大型数据集 该数据集是由不同的人长时间编写的 因此 数据不采用单一格式 例如 在 作者 栏中我可以找到John Smith Smith John Smith J等 但它们是同一个人 我连最简单的动作都做不了 例如
  • sapply - 保留列名称

    我试图总结数据集中许多不同列 变量 的平均值 标准差等 我已经编写了自己的汇总函数 以准确返回我需要和正在使用的内容sapply立即将此函数应用于所有变量 它工作正常 但是返回的数据帧没有列名 我似乎甚至无法使用列号引用重命名它们 也就是说
  • 闪亮的应用程序包:css 和所有 www/ 目录内容

    我正在尝试将 Shiny 应用程序转换为 R 包 但我在处理有关 www 目录以及 松散 文件的所有问题时遇到了问题 我闪亮的应用程序运行得很好 但是当我尝试 打包它 时 它不起作用 我闪亮的应用程序目录 my shiny app R ut
  • 从 data.frame 在 ggplot 图例中添加信息

    我想在图例中添加信息 哪个传感器具有该值 这是我的代码 z lt data frame a c sensor 1 sensor 2 sensor 3 sensor 4 sensor 5 sensor 6 sensor 7 sensor 8
  • 如何声明包含 M 个元素的列表对象

    我想声明一个包含 M 3 x 3 矩阵的列表 如果我事先知道数字 M 那么我可以通过以下方式声明这样的列表 elm lt matrix NA 3 3 Say M 7 myList lt list elm elm elm elm elm el
  • R,使用具有两种以上可能性的二项式分布

    我知道这可能是基本的 但我似乎有一个心理障碍 假设您想要计算在一个骰子上掷出 4 5 或 6 的概率 在 R 中 这很简单 sum 1 6 1 6 1 6 这给出了 1 2 这是正确答案 然而 我内心深处 可能应该保留的地方 认为我应该能够
  • 在包加载之前如何知道 R 中特定函数属于哪个包?

    例如 我知道许多流行的功能 例如tbl df 我通常不记得它属于哪个包 即data table or dplyr 所以我必须始终记住并加载一个包 但我做不到 tbl df除非我加载了正确的包 在 R 控制台本身加载或安装包之前 有没有办法知
  • 为什么这个 R ggplot2 代码会显示一个空白的显示设备?

    虽然 SO 通常不用于帮助解决错误 但这个显示了特别简单且特别烦人的行为 如果你是一个ggplot2用户 您可以在 10 秒或更短的时间内重现它 正如这个 GitHub 问题 ggplot gtable 创建空白显示 https githu
  • 从数据框中绘制多条平滑线

    我对 R 比较陌生 我正在尝试绘制从 csv 文件加载的数据框 数据由 6 列组成 如下所示 xval col1 col2 col3 col4 col5 第一列 xval 由一系列单调递增的正整数 例如 10 40 60 等 组成 其他列
  • case_when 与部分字符串匹配和 contains()

    我正在使用一个数据集 其中有许多名为 status1 status2 等的列 在这些列中 它表示某人是否豁免 完整 注册等 不幸的是 豁免投入并不一致 这是一个示例 library dplyr problem lt tibble perso

随机推荐