2

我想在单个页面上监控 R 中生成的数字的基本质量,例如每页的字节大小,......我现在只能对平均页面进行质量保证,请参阅下面的章节。我认为该任务必须有一些内置的东西而不是平均措施。

产生4页的代码,Rplots.pdf我想知道输出中每页的字节大小;也欢迎页面输出的任何其他统计信息;你可以在这里通过对象获得基本的内存监控,但我希望它对应于 PDF 中的输出

# https://stat.ethz.ch/R-manual/R-devel/library/graphics/html/plot.html
require(stats) # for lowess, rpois, rnorm
plot(cars)
lines(lowess(cars))

plot(sin, -pi, 2*pi) # see ?plot.function

## Discrete Distribution Plot:
plot(table(rpois(100, 5)), type = "h", col = "red", lwd = 10,
     main = "rpois(100, lambda = 5)")

## Simple quantiles/ECDF, see ecdf() {library(stats)} for a better one:
plot(x <- sort(rnorm(47)), type = "s", main = "plot(x, type = \"s\")")
points(x, cex = .5, col = "dark red")

## TODO summarise here the byte size of figures in the figures (1-4)
# Output: Rplot.pdf where 4 pages; I want to know the size of each page in bytes

我目前正在命令行中进行基本的质量保证,但想将其中的一些移到 R 中,以更快地观察错误。

预期输出:字节大小,例如第 4 列ls -l

获取输出文档中平均单个页面的字节大小

限制

  • 要求页面中数据的同质性​​。此方法仅适用于所有页面均来自同一样本的情况。否则很麻烦,因为它只是平均的,没有描述个别现象。其他可能的弱点
  • PDF 元素和元数据。整体考虑 pdf 文件,而不是关注图形对象本身。所以这限制了绝对值的使用,因为文件大小还包含标题和其他与图形对象无关的元数据。

代码

filename <- "main.pdf"
filesize <- file.size(filename)
# http://unix.stackexchange.com/q/331175/16920
pages <- Rpoppler::PDF_info(filename)$Pages 

# print page size (= filesize / pages)
pagesize <- filesize / pages

## data of example file 
num 7350960
int 62
num 118564

输入:任何 62 页文档
输出:平均单个页面大小 (118564)

测试答案

输出,但您不能轻松地将输入更改为您想要的 pdf 文件

     files                             size_bytes 
[1,] "./test_page_size_pdf/page01.pdf" "4,123,942"
[2,] "./test_page_size_pdf/page02.pdf" "    4,971"
[3,] "./test_page_size_pdf/page03.pdf" "    4,672"
[4,] "./test_page_size_pdf/page04.pdf" "    5,370"

输入:任何 64 页文档
预期输出:67 (= 64 + 3) 页,而不是 4 页已分析

R:3.3.2
操作系统:Debian 8.5

4

2 回答 2

4

如果您的系统上还没有 pdftk 实用程序,请下载并安装它,然后从 R 中尝试以下替代方法之一。

1)它将返回一个数据帧,其中包含页面文件大小(以字节为单位)和其他信息。

myfile <- "Rplots.pdf"
system(paste("pdftk", myfile, "burst"))
file.info(Sys.glob("pg_*.pdf"))

它还将生成一个文件 doc_data.txt,其中包含一些可能感兴趣也可能不感兴趣的杂项信息。

1a)此替代方法不会生成任何文件。它只会将页面的字符大小作为数字向量返回。

myfile <- "Rplots.pdf"
pages <- as.numeric(read.dcf(pipe(paste("pdftk", myfile, "dump_data")))[, "NumberOfPages"])
cmds <- sprintf("pdftk %s cat %d output - | wc -c", myfile, seq_len(pages))
unname(sapply(cmds, function(cmd) scan(pipe(cmd), quiet = TRUE)))

pdftk如果并且wc在您的道路上,上述内容应该有效。请注意,在 Windows 上,您可以wc在 Rtools 发行版中找到,并且通常会在"C:\\Rtools\\bin\\wc"安装 Rtools 时立即找到。

2)这个替代方案类似于(1),但使用动画包:

library(animation)

ani.options(pdftk = "/path/to/pdftk")
pdftk("Rplots.pdf", "burst", "pg_%04d.pdf", "")
file.info(Sys.glob("pg_*.pdf"))
于 2016-12-23T03:03:49.523 回答
2

要测量 pdf 文件中每一页的大小,我建议这样做:

test_size <- TRUE
pdf_name <- "masterpiece"

if(test_size){
  dir.create("test_page_size_pdf")
  pdf_address <- paste0("./test_page_size_pdf/page%02d.pdf")  
} else { pdf_address <- paste0("./", pdf_name, ".pdf")}

pdf(pdf_address, width=10, height=6, onefile=!test_size)
par(mar=c(1,1,1,1), oma=c(1,1,1,1))

  plot(rnorm(10^6, 100, 5), type="l")
  plot(sin, -pi, 2*pi) 
  plot(table(rpois(100, 5)), type = "h", col = "red", lwd = 10,
     main = "rpois(100, lambda = 5)")
  plot(x <- sort(rnorm(47)), type = "s", main = "plot(x, type = \"s\")")
  points(x, cex = .5, col = "dark red")

dev.off()

if(test_size){
  files <- paste0("./test_page_size_pdf/", list.files("./test_page_size_pdf/"))
  size_bytes <- format(file.size(files), big.mark = ",")
  file.remove(files)
  file.remove("test_page_size_pdf")
  cbind(files, size_bytes)
}

R 中 pdf 页面的大小取决于三件事: 的内容、函数plot()中使用的pdf()选项以及此处定义的绘图选项par()

这一切都难以估计。你还提到你喜欢有类似于 shell 函数的东西ls,它也可以在文件上运行。所以在这个解决方案中,我创建了一个临时文件夹dir.create(),我们在其中将 pdf 的每一页分别保存在一个文件中。我们使用选项来实现这一点onefile。绘图完成后,每个 pdf 页面文件以及临时文件夹都将被删除。您可以在控制台中看到结果。

如果您已完成测试并希望将结果保存在单个文件中,则只需在此脚本的第一行中更改变量test_size <- FALSE. 顺便一提; 我怀疑页面大小是否代表图像质量。Pdf 是矢量格式,因此大小与元素数量相对应:请参阅我的示例中第一页的大小,其中我绘制了 1mio 点。

于 2016-12-18T14:47:04.143 回答