我正在构建一个广泛使用子文档的报告基础结构(通过{r, child = 'somedir/child_doc.Rmd'}
)并通过主文档的params
标题中的YAML
字典进行参数化。一个例子可能是:
---
title: Project Report
subtitle: POIGNANT DESCRIPTION OF THE WORK AT HAND
date: '`r format(Sys.time(), "%d %B, %Y")`'
output:
bookdown::pdf_document2:
template: ~
toc: yes
toc_depth: 2
colorlinks: yes
fontsize: 11pt
documentclass: scrartcl
geometry: margin=1in, a4paper
params:
submodule:
value:
intro:
data_dir: 'data'
---
使用此结构,访问data_dir
会出现问题,因为主文档和子文档的工作目录不同,因此相对路径定义也有所不同。方法是:
在定义data_dir
时使用绝对/扩展路径名。 快速变得长/笨重。
params
对象的后处理,以扩展主文档中的路径。从params
块内部访问时R
是不可变的,这只能以不优雅的方式解决:
```{r params-processing, include = FALSE}
local_params <- params
local_params$submodule$intro$data_dir <- path.expand(local_params$submodule$intro$data_dir)
其次是内部使用local_params
代替params
。
在!R path.expand('data')
标题中定义参数时,使用YAML
之类的内容扩展路径。虽然这个(或基于`的等价物)适用于示例中的data
字段,但knitr
在路径案例中失败,因为R
表达式是不已展开但用作字符表示 - 文字"path.expand('data')"
显然不存在作为路径。
我很欣赏有关如何解决这个问题的任何提示 - 尤其是3.是否可以实现......
答案 0 :(得分:5)
source code of r-yaml
(由bookdown::render_book
隐式调用)表明您可以通过使用expr
标记解析相对路径,轻松地解决选项3:
params:
submodule:
value:
intro:
data_dir: !expr normalizePath('data')
这将评估YAML中的R表达式,不需要任何进一步处理。
data_dir: !r normalizePath('data')
也是可接受的语法,由knitr
处理。不幸的是,只有!R
或`r
,你试过的两个都被解释了。
我还建议使用normalizePath
,因为它返回给定任何相对目录的绝对路径。您使用path.expand
的示例仅执行波浪线扩展,因此对'data'
等本地相对路径没有影响。 normalizePath
实际上是path.expand
作为第一步。
只需照常访问完全展开的路径
```{r params-processing}
print(params$submodule$intro$data_dir)
```
## $value
## [1] "/Users/user_name/full_path_to_book/my_book/data"
##
## $expr
## [1] "normalizePath('data')"
##
## attr(,"class")
## [1] "knit_param_expr"
请注意,最好使用!r
看到r-yaml
行为可能会因为当前发出警告而发生变化:
Warning message:
In yaml.load(readLines(con), error.label = error.label, ...) :
R expressions in yaml.load will not be auto-evaluated by default in the near future