R knitr:是否可以通过编程方式修改块标签?
我试图使用knitr生成一个报告,该报告在数据集的不同子集上执行相同的分析集。该项目包含两个Rmd文件:第一个文件是设置工作区和文档的主文档,第二个文件仅包含执行分析和生成关联图形的块 我想做的是编织主文件,然后为每个数据子集调用第二个文件,并将结果包含在单个文档中。下面是一个简单的例子 主文件:R knitr:是否可以通过编程方式修改块标签?,r,knitr,R,Knitr,我试图使用knitr生成一个报告,该报告在数据集的不同子集上执行相同的分析集。该项目包含两个Rmd文件:第一个文件是设置工作区和文档的主文档,第二个文件仅包含执行分析和生成关联图形的块 我想做的是编织主文件,然后为每个数据子集调用第二个文件,并将结果包含在单个文档中。下面是一个简单的例子 主文件: # My report ```{r} library(iterators) data(mtcars) ``` ```{r create-iterator} cyl.i <- iter(uni
# My report
```{r}
library(iterators)
data(mtcars)
```
```{r create-iterator}
cyl.i <- iter(unique(mtcars$cyl))
```
## Generate report for each level of cylinder variable
```{r cyl4-report, child='analysis-template.Rmd'}
```
```{r cyl6-report, child='analysis-template.Rmd'}
```
```{r cyl8-report, child='analysis-template.Rmd'}
```
但knitr似乎不会在块标签位置计算表达式
我还尝试使用修改当前块标签的自定义块:
knit_hooks$set(cyl.suffix = function(before, options, envir) {
if (before) options$label <- "new-label"
})
knit_hooks$set(cyl.suffix=函数(before,options,envir){
if(before)options$label如果您将**中的所有块都设为无名,即,`{r}
它就可以工作了。这当然不是很优雅,但有两个问题阻止您更改当前块的标签:
在执行代码块之前解析文件。在执行任何代码或调用自定义挂钩之前,解析器已经检测到重复的标签
块选项(包括标签)是在调用钩子之前处理的(逻辑:它是一个触发钩子的选项),因此钩子不能再更改标签
未命名块工作的事实是,它们在内部获得标签unnamed chunk-
+chunk number
块不能有重复的名称,因为内部knitr通过标签引用它们。修复方法可以是让knitr将块编号添加到所有具有重复名称的块中。或者通过块编号而不是标签引用它们,但在我看来,这是一个更大的变化。对于任何看到这篇文章的人,我想指出@Yih通过引入knit\u expand()
函数,用户界面在knitr 1.0中为这个问题提供了一个解决方案。它工作得很好,并且确实简化了我的工作流程
例如,下面将为每一级别的mtcars$cyl
处理下面的模板脚本,每次将{{ncyl}}
的所有实例(在模板中)替换为其当前值:
# My report
```{r}
data(mtcars)
cyl.levels <- unique(mtcars$cyl)
```
## Generate report for each level of cylinder variable
```{r, include=FALSE}
src <- lapply(cyl.levels, function(ncyl) knit_expand(file = "template.Rmd"))
```
`r knit(text = unlist(src))`
提出了一个类似的问题,我能够使用knit_expand(text=)和r paste(knitr::knit(text=paste(out,collapse='\n'))以编程方式创建r块,并根据任意输入图列表在flexdashboard中编织输出(非常有用)
methods.您的理解完全正确,这是一个令人信服的案例,knitr需要一些更改。我现在正在查看您的请求。谢谢!@Rolo,您对knitr内部工作原理的解释非常有用。我非常感谢您花时间编写。@Yihui,您认为您会包括此更改吗?它会ld解决了我试图完成的90%的问题,这使得我无需维护Rmd文件的副本,这些副本除了修改的区块标签外都是相同的。理想的解决方案是允许(I in unique(mtcars$cyl))knit_child(“analysis template.Rmd”,label.suffix=I)的
,如果可能的话。是的,我想我倾向于接受拉取请求;再给我几分钟,因为我还有两个备选解决方案。解决这个问题很容易,但很难决定使用哪个解决方案。我使用了这种方法,但注意到在模板中使用echo=FALSE
,会导致代码未被处理。您是否注意到相同的行为?编辑:我在bookdown软件包中使用了这种方法,并注意到在模板中使用results='asis'
和echo=FALSE
会导致代码未被处理。解决方法是将每个输出放在单独的代码块中。
knit_hooks$set(cyl.suffix = function(before, options, envir) {
if (before) options$label <- "new-label"
})
# My report
```{r}
data(mtcars)
cyl.levels <- unique(mtcars$cyl)
```
## Generate report for each level of cylinder variable
```{r, include=FALSE}
src <- lapply(cyl.levels, function(ncyl) knit_expand(file = "template.Rmd"))
```
`r knit(text = unlist(src))`
```{r, results='asis'}
cat("### {{ncyl}} cylinders")
```
```{r mpg-histogram-{{ncyl}}cyl}
hist(mtcars$mpg[mtcars$cyl == {{ncyl}}],
main = paste({{ncyl}}, "cylinders"))
```
```{r weight-histogam-{{ncyl}}cyl}
hist(mtcars$wt[mtcars$cyl == {{ncyl}}],
main = paste({{ncyl}}, "cylinders"))
```