这是tidyverse 对您的问题的看法,这可以说是非常冗长。一些解释:
1) 第一个 mutate() 块将两个 Delta 列四舍五入以具有一个有效数字并将其转换为一个字符;这样可以保留长度。
2) 第二个 mutate() 块将“正常”x 和 y 列四舍五入,使其长度与 Delta 列相同。 - 2L 避免了基于. 之前的数字和. 本身在Delta 列中的错误舍入。
3) 第三个mutate() 块首先处理两种“不寻常”的情况:第一个if_else() 处理四舍五入的y 数字没有. 和数字,但@ 987654336@ 值可以。第二个if_else() 处理舍入过程中的最后一位数字是0 的情况,而R 舍入时会下降。对x 列重复这两种措施。
4) 第四个mutate() 块在x 和y 列中的值末尾添加空格,以确保错误编号对齐。
5) 最后的unite() 和mutate() 命令合并列并为第二个数字添加括号。
library("tidyverse")
library("knitr")
df %>%
mutate(Delta.x = signif(Delta.x, digits = 1L),
Delta.x = as.character(Delta.x),
Delta.y = signif(Delta.y, digits = 1L),
Delta.y = as.character(Delta.y)) %>%
mutate(x = round(x, digits = str_count(Delta.x) - 2L),
x = as.character(x),
y = round(y, digits = str_count(Delta.y) - 2L),
y = as.character(y)) %>%
mutate(y = if_else(condition = str_count(y, "\\.") == 0,
true = str_c(y, str_dup("0", str_count(Delta.y) - str_count(y) - 1L), sep = "."),
false = y),
y = if_else(condition = str_count(Delta.y) - str_count(y) != 0,
true = str_c(y, str_dup("0", times = str_count(Delta.y) - str_count(y))),
false = y),
x = if_else(condition = str_count(x, "\\.") == 0,
true = str_c(x, str_dup("0", str_count(Delta.x) - str_count(x) - 1L), sep = "."),
false = x),
x = if_else(condition = str_count(Delta.x) - str_count(x) != 0,
true = str_c(x, str_dup("0", times = str_count(Delta.x) - str_count(x))),
false = x)) %>%
mutate(x = if_else(condition = str_count(x) < max(str_count(x)),
true = str_c(x, str_dup(" ", times = max(str_count(x)) - str_count(x))),
false = x),
y = if_else(condition = str_count(y) < max(str_count(y)),
true = str_c(y, str_dup(" ", times = max(str_count(y)) - str_count(y))),
false = y)) %>%
unite(x, x, Delta.x, sep = " (") %>%
unite(y, y, Delta.y, sep = " (") %>%
mutate(x = str_c(x, ")"),
y = str_c(y, ")")) %>%
kable()
|x |y |
|:-----------|:-------------|
|1.0 (0.1) |0.20 (0.01) |
|0.12 (0.07) |0.8 (0.1) |
|0.71 (0.03) |0.18 (0.09) |
|0.63 (0.02) |0.805 (0.003) |
|0.27 (0.09) |0.106 (0.008) |
此外,您可以设置全局options(scipen = 999)(或任何其他大数字)以避免数字的科学表示,例如2e-5(在您的 kable 中应该看起来像 0.00002)。
编辑:更新并澄清了一些命令。
更新(Javi_VM)
我只是把它变成了一个函数。您可以提供 2 个向量或 1 个带有两列的 data.frame。它仍然缺乏对科学记数法的支持(例如 1.05 10^9),但可以开始。
scinumber <- function(df=NULL, x, Delta.x){
if (is.null(df)) {
df <- data.frame(
x = x,
Delta.x = Delta.x
)
} else {
colnames(df)[colnames(df)==x] <- "x"
colnames(df)[colnames(df)==Delta.x] <- "Delta.x"
}
require(tidyverse)
options(scipen = 999)
output <-
df %>%
mutate(Delta.x = signif(Delta.x, digits = 1L),
Delta.x = as.character(Delta.x)) %>%
mutate(x = round(x, digits = str_count(Delta.x) - 2L),
x = as.character(x)
) %>%
mutate(x = if_else(condition = str_count(x, "\\.") == 0,
true = str_c(x, str_dup("0", str_count(Delta.x) - str_count(x) - 1L), sep = "."),
false = x),
x = if_else(condition = str_count(Delta.x) - str_count(x) != 0,
true = str_c(x, str_dup("0", times = str_count(Delta.x) - str_count(x))),
false = x)) %>%
mutate(x = if_else(condition = str_count(x) < max(str_count(x)),
true = str_c(x, str_dup(" ", times = max(str_count(x)) - str_count(x))),
false = x)) %>%
unite(x, x, Delta.x, sep = " (") %>%
mutate(x = str_c(x, ")"))
return(output)
}