如何使用 write.table 将数据帧下载到漂亮的 csv/Excel 文件中?
How to use write.table to download a dataframe into a nice csv/Excel file?
我正在尝试使用 Shiny downloadHandler()
中的 write.table()
函数,根据底部的可重现代码,将 df
反应性数据帧下载为 .csv 文件。函数 write.table()
允许删除列名(我需要)但会导致非 Excel 输出(问题 #1);另一方面,write.csv()
会产生不错的 Excel 输出,但不允许删除列名(问题 #2)。
有没有办法让 write.table()
为 CSV 正常工作?如果不行,有没有其他办法解决?
此图显示了问题:
可重现代码:
library(dplyr)
library(DT)
library(shiny)
library(shinyWidgets)
library(tidyverse)
ui <-
fluidPage(fluidRow(
column(width = 8,
h3("Click below to download:"),
downloadButton("sumsDownload","Download",style = "width:20%;"),
h3("Summed Data:"),
DT::dataTableOutput("sums")
)
))
server <- function(input, output, session) {
data <- reactive({
data.frame(
Period = c("2020-01", "2020-02", "2020-03", "2020-01", "2020-02", "2020-03"),
ColA = c(1000.01, 20, 30, 40, 50, 60),
ColB = c(15.06, 25, 35, 45, 55, 65)
)
})
summed_data <- reactive({
data() %>%
group_by(!!sym("Period")) %>%
select("ColA", "ColB") %>% summarise(across(everything(), sum))
})
output$sums <- renderDT({datatable(data = summed_data(),rownames = FALSE)})
df <- reactive({ # `df` modifies `summed_data` for csv download
as.data.frame(
rbind(
c("Summed Data",rep(NA,ncol(summed_data())-1)),
colnames(summed_data()),
matrix(unlist(summed_data(), use.names=FALSE),
nrow = nrow(summed_data()),
)
)
)
})
output$sumsDownload <- downloadHandler(
filename = function() {paste("sumsDownload","csv",sep=".")},
content = function(file){
write.table( # change this to write.csv to see Issue #2
df(),
na = "",
file,
col.names = FALSE, # comment out this line if changing to write.csv
row.names = FALSE)
}
)
}
shinyApp(ui, server)
以下是已解决的代码,反映了 2022 年 5 月 5 日之前发布的评论:
library(dplyr)
library(DT)
library(shiny)
library(shinyWidgets)
library(tidyverse)
ui <-
fluidPage(fluidRow(
column(width = 8,
h3("Click below to download:"),
downloadButton("sumsDownload","Download",style = "width:20%;"),
h3("Summed Data:"),
DT::dataTableOutput("sums")
)
))
server <- function(input, output, session) {
data <- reactive({
data.frame(
Period = c("2020-01", "2020-02", "2020-03", "2020-01", "2020-02", "2020-03"),
ColA = c(1000.01, 20, 30, 40, 50, 60),
ColB = c(15.06, 25, 35, 45, 55, 65)
)
})
summed_data <- reactive({
data() %>%
group_by(!!sym("Period")) %>%
select("ColA", "ColB") %>% summarise(across(everything(), sum))
})
output$sums <- renderDT({datatable(data = summed_data(),rownames = FALSE)})
df <- reactive({ # `df` modifies `summed_data` for csv download
as.data.frame(
rbind(
c("Summed Data",rep(NA,ncol(summed_data())-1)),
colnames(summed_data()),
matrix(unlist(summed_data(), use.names=FALSE),
nrow = nrow(summed_data()),
)
)
)
})
output$sumsDownload <- downloadHandler(
filename = function() {paste("sumsDownload","csv",sep=".")},
content = function(file){
write.table(
df(),
na = "",
file,
sep = ",", # add this per road_to_quantdom on May/05/22
col.names = FALSE,
row.names = FALSE)
}
)
}
shinyApp(ui, server)
我正在尝试使用 Shiny downloadHandler()
中的 write.table()
函数,根据底部的可重现代码,将 df
反应性数据帧下载为 .csv 文件。函数 write.table()
允许删除列名(我需要)但会导致非 Excel 输出(问题 #1);另一方面,write.csv()
会产生不错的 Excel 输出,但不允许删除列名(问题 #2)。
有没有办法让 write.table()
为 CSV 正常工作?如果不行,有没有其他办法解决?
此图显示了问题:
可重现代码:
library(dplyr)
library(DT)
library(shiny)
library(shinyWidgets)
library(tidyverse)
ui <-
fluidPage(fluidRow(
column(width = 8,
h3("Click below to download:"),
downloadButton("sumsDownload","Download",style = "width:20%;"),
h3("Summed Data:"),
DT::dataTableOutput("sums")
)
))
server <- function(input, output, session) {
data <- reactive({
data.frame(
Period = c("2020-01", "2020-02", "2020-03", "2020-01", "2020-02", "2020-03"),
ColA = c(1000.01, 20, 30, 40, 50, 60),
ColB = c(15.06, 25, 35, 45, 55, 65)
)
})
summed_data <- reactive({
data() %>%
group_by(!!sym("Period")) %>%
select("ColA", "ColB") %>% summarise(across(everything(), sum))
})
output$sums <- renderDT({datatable(data = summed_data(),rownames = FALSE)})
df <- reactive({ # `df` modifies `summed_data` for csv download
as.data.frame(
rbind(
c("Summed Data",rep(NA,ncol(summed_data())-1)),
colnames(summed_data()),
matrix(unlist(summed_data(), use.names=FALSE),
nrow = nrow(summed_data()),
)
)
)
})
output$sumsDownload <- downloadHandler(
filename = function() {paste("sumsDownload","csv",sep=".")},
content = function(file){
write.table( # change this to write.csv to see Issue #2
df(),
na = "",
file,
col.names = FALSE, # comment out this line if changing to write.csv
row.names = FALSE)
}
)
}
shinyApp(ui, server)
以下是已解决的代码,反映了 2022 年 5 月 5 日之前发布的评论:
library(dplyr)
library(DT)
library(shiny)
library(shinyWidgets)
library(tidyverse)
ui <-
fluidPage(fluidRow(
column(width = 8,
h3("Click below to download:"),
downloadButton("sumsDownload","Download",style = "width:20%;"),
h3("Summed Data:"),
DT::dataTableOutput("sums")
)
))
server <- function(input, output, session) {
data <- reactive({
data.frame(
Period = c("2020-01", "2020-02", "2020-03", "2020-01", "2020-02", "2020-03"),
ColA = c(1000.01, 20, 30, 40, 50, 60),
ColB = c(15.06, 25, 35, 45, 55, 65)
)
})
summed_data <- reactive({
data() %>%
group_by(!!sym("Period")) %>%
select("ColA", "ColB") %>% summarise(across(everything(), sum))
})
output$sums <- renderDT({datatable(data = summed_data(),rownames = FALSE)})
df <- reactive({ # `df` modifies `summed_data` for csv download
as.data.frame(
rbind(
c("Summed Data",rep(NA,ncol(summed_data())-1)),
colnames(summed_data()),
matrix(unlist(summed_data(), use.names=FALSE),
nrow = nrow(summed_data()),
)
)
)
})
output$sumsDownload <- downloadHandler(
filename = function() {paste("sumsDownload","csv",sep=".")},
content = function(file){
write.table(
df(),
na = "",
file,
sep = ",", # add this per road_to_quantdom on May/05/22
col.names = FALSE,
row.names = FALSE)
}
)
}
shinyApp(ui, server)