使用Shiny中的多个条目对子数据集进行子集设置会产生错误的输出

时间:2015-12-06 23:07:30

标签: r ggplot2 shiny data.table

我正在创建一个Shiny应用程序,当我在selectizeInput框中选择多个输入并尝试使用这些选项对我的数据进行子集时,我遇到了问题。

这是预期的输出

testDT <- data.table(
    L = (1:32), 
    M = rep(letters[23:26], each = 64), 
    N = rep(LETTERS[1:2], times = 2, each = 512),
    O = rnorm(2048, 1))

testDT$L <- factor(testDT$L, levels = seq(from = 1, to = 32, by = 1))

ggplot(testDT, aes(L,O)) +
    geom_boxplot(aes(fill = N)) +  
    theme_bw() +
    theme(legend.position = "top", legend.title=element_blank()) + 
    facet_grid(M ~ ., scales = "free") +
    labs(x = "L", y = "O")

但是,当我创建应用程序时,图形输出不是预期的。我选择的选项越多,例如在N中,似乎数据开始交替。

这是ui.R文件:

# ui.R

shinyUI(fluidPage(

            titlePanel("Test Application"),

            sidebarLayout(
                    sidebarPanel(

                            selectizeInput("N",
                                    label = ("N"),
                                    multiple = TRUE,
                                    choices = NULL,
                                    options = list(
                                            placeholder = 'Select All Desired, Type to Search',
                                            onInitialize = I('function() { this.setValue(""); }')
                                    )),

                            selectizeInput("M", 
                                    label = "M",
                                    multiple = TRUE,
                                    choices = NULL,
                                    options = list(
                                            placeholder = 'Select All Desired, Type to Search',
                                            onInitialize = I('function() { this.setValue(""); }')
                                    ))
                    ),

                    mainPanel(
                            tabsetPanel(
                                    tabPanel("Test Plot 1",
                                            plotOutput("testPlot1")),
                                    tabPanel("Test Plot 2",
                                            plotOutput("testPlot2"))


                    )
            ))))

这是server.R文件:

# server.R

library(data.table)
library(ggplot2)

testDT <- data.table(
    L = (1:32), 
    M = rep(letters[23:26], each = 64), 
    N = rep(LETTERS[1:2], times = 2, each = 512),
    O = rnorm(2048, 1))

testDT$L <- factor(testDT$L, levels = seq(from = 1, to = 32, by = 1))

shinyServer(function(input, output, session) {

        updateSelectizeInput(session, "N", 
                server = TRUE, 
                choices = sort(unique(testDT$N)),
        )

        updateSelectizeInput(session, "M", 
                server = TRUE, 
                choices = unique(testDT$M),
        )       

        testDT1 <- reactive({
                    subset(testDT, N == input$N)
                })

        testDT2 <- reactive({
                    subset(testDT, N == input$N & M == input$M)
                })

        output$testTable <- renderDataTable(testDT1())

        output$testPlot1 <- renderPlot({

                    p <- ggplot(testDT1(), aes(L,O)) +
                            geom_boxplot(aes(fill = N)) +  
                            theme_bw() +
                            theme(legend.position = "top", legend.title=element_blank()) + 
                            facet_grid(M ~ ., scales = "free") +
                            labs(x = "L", y = "O")
                    print(p)
                })

        output$testPlot2 <- renderPlot({

                    p <- ggplot(testDT2(), aes(L,O)) +
                            geom_boxplot(aes(fill = N)) +  
                            theme_bw() +
                            theme(legend.position = "top", legend.title=element_blank()) + 
                            facet_grid(M ~ ., scales = "free") +
                            labs(x = "L", y = "O")
                    print(p)
                })
    })

我非常怀疑我是否错误地对数据进行了子集化,但由于我是Shiny环境的新用户,因此我无法完全理解使用input$_____调用进行子集化时的行为,例如下面。

testDT1 <- reactive({
      subset(testDT, N == input$N)
      })

1 个答案:

答案 0 :(得分:2)

我建议使用[运算符的子集而不是subset函数 有关详细信息,请阅读问题In R, why is [ better than subset? 在您的示例中:

testDT1 <- reactive({
      testDT[eval(call("==", as.name("N"), input$N))]
})

针对多值子集将==更改为%in%

另外请注意,使用data.table索引可能是值得的,因为它可以大大加快过滤速度,因此可以为您闪亮的应用程序提供实时过滤。有关详细信息,请参阅我的博文Scaling data.table using index 实际上索引应该在第一次过滤期间自动创建,您可以在使用set2keyv函数加载数据集后进行准备。