【问题标题】:Convert Number Stored as Text in Excel File Using R使用 R 转换 Excel 文件中存储为文本的数字
【发布时间】:2019-08-29 17:44:45
【问题描述】:

我想将数据从 R 输出到一个 excel 文件,并且一直在使用 openxlsx 包。

writeDataTable 是我一直在使用的函数。问题是我希望其中一列的条目是数字和文本的混合。由于 R 中数据框的一列必须具有所有相同类型的条目,因此所有内容都将转换为字符条目。

当我打开输出的 excel 文件时,我会在数字单元格的角落看到一个绿色的小三角形,告诉我它们是以文本形式存储的数字,并让我可以选择转换为数字。

我想知道是否可以让 R 在保存文件之前创建的工作簿对象中为我转换它。

我花了很多时间在谷歌上搜索这个问题,寻找可能有帮助的不同库,但到目前为止还没有找到任何东西。我有一个下面的例子。请注意,这不是我使用的确切数据框,而是用于演示目的。

df = data.frame(A = c('Dog', '5', '7.04'), B = c('Cat', '12', '1.23'))
wb = createWorkbook()
addWorksheet(wb, "Sheet2")
writeDataTable(wb, "Sheet2", df)
output_file = "C:\\Users\\johndoe\\documents\\excel_file.xlsx"
saveWorkbook(wb, output_file)

任何帮助将不胜感激。

【问题讨论】:

  • 我用library(xlsx) \ write.xlsx(mydata, "c:/mydata.xlsx")
  • @TJ87,我认为这不能解决混合类列问题。
  • 一种解决方法是创建一个带有两个选项卡的 template.xlsx。一个带有Data 选项卡的writeData 进入另一个选项卡Formula 具有Excel 公式到Data 选项卡,例如单元格 A2 =Data!A2。不理想(但会去掉绿色三角形),因为您首先需要将公式复制到 template.xlsx 中,并且文件大小会加倍,因为您要保留两个相同数据的选项卡
  • 感谢 MKa,这绝对是一个可行的解决方法。是否可以在 R 中复制然后粘贴值,以便删除“数据”选项卡?然后是否可以将“公式”选项卡的一部分格式化为表格(我正在处理的数据将具有可变数量的行,因此无法预先格式化表格)。无论如何,我想我会尝试下面的 r2evans 方法,但最好有尽可能多的解决方案。

标签: r excel openxlsx


【解决方案1】:

这是一种方法,但它会非常缓慢。

### unchanged
library(openxlsx)
df = data.frame(A = c('Dog', '5', '7.04'), B = c('Cat', '12', '1.23'))
wb = createWorkbook()
addWorksheet(wb, "Sheet2")
writeDataTable(wb, "Sheet2", df)

### this is the new part
for (cn in seq_len(ncol(df))) {
  for (rn in seq_len(nrow(df))) {
    if (!is.numeric(df[rn,cn]) && !is.na(val <- as.numeric(as.character(df[rn,cn])))) {
      writeData(wb, "Sheet2", val, startCol = cn, startRow = 1L + rn)
    }
  }
}

### unchanged
saveWorkbook(wb, output_file)

问题是一次写入一个单元格。

改进方法:

  • 如果您的数字多于字符串,您可能希望通过使用 as.numeric 转换相关列(产生大量 NAs)来稍微反转这一点,然后一个接一个地结束- 用前一个字符串写入单元格的NA 值。

  • 您可以查找要替换的单元格运行(可能在列中使用rle),这将逐个地写入而不是逐个单元格。

【讨论】:

  • 感谢 r2evans。我一定会试试这个。实际上没有很多非数字值,所以我可能会尝试您建议的相反方式。从未考虑过覆盖由于某种原因已经写入的值。显然不想使用 for 循环,但我找不到方法,所以这似乎是一个合理的解决方案。将数据类型写入 excel 对象后,您将无法更改数据类型,这似乎很奇怪。
  • 是的,我正在想办法以“透明度”推送矩阵(即NA时不要输入值”),但我不认为这种逻辑存在。如果openxlsx 使用内部(C++)for 循环,那么这样做实际上是可行的,也许您可​​以请求它。 (不幸的是,last commit 似乎是 2018 年 8 月......没有希望。)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多