作者:万莉 (北京航空航天大学)
连享会 - 与君分享 lianxh.cn
文章目录
引言
在 Stata 16 发布页面, “truly reproducible reporting(可重复性报告)” 成为亮点之一。继 Stata 15 之后, Stata16 进一步引入和完善一系列相关命令。
对于 Stata 用户而言,我们可以用这些命令直接编写 dofile, 将报告正文、Stata 生成的图表等整合在一个文档中,自定义生成各种格式的文档(text,Word,PDF,Excel 或 HTML)。
更为重要的是,我们可实现可重复性研究,即报告中的数据、模型发生变化后,我们只需稍加修改 Stata 命令,便可输出更新后的文档,而不必逐个修改变动后的结果。
生成可重复性报告(Reproducible and automated reporting)的命令可分为两类:
-
第一类:dyn 类——生成文档: 各种带
dyn
前缀的动态文档生成命令 (如dyntext
|dyndoc
),用于生成 text、HTML 和 Word 文档。更重要的是,该命令支持 Markdown 文本格式语言。 -
第二类:put 类——输出文档: 各种带
put
前缀的文档输出命令 (putdocx
|putpdf
|putexcel
)。此类命令可自定义生成 Word、PDF 和 Excel 文件。
本文着重讲解第一类命令的使用方法。后续将介绍第二类命令。
连享会计量方法专题……
1. 准备工作:Markdown 和 Stata 动态标签
在学习动态文档命令前,我们先做一些准备工作。由于该类命令支持 Markdown 文本格式语言,且需要包含 Stata dynamic tags(动态标签),我们先大致了解下 Markdown 和 Stata dynamic tags(动态标签)。
1.1 什么是 Markdown ?
Markdown 是一种轻量级且易使用的标记语言,通过对标题、正文、加粗、链接等主要文本格式的预设编码,帮用户在写作中有效避免频繁的格式调整,获得更加流畅沉浸的写作体验。本质上,Markdown 是一种标记语法,它的格式更接近于纯文本。
了解 Markdown 的核心语句只需要五分钟。对比下图左右两栏,即可快速掌握 9 成以上的 Markdown 语法 ( Source: 「连玉君-五分钟 Markdown 教程」)。
- Markdown 语法的入门教程:
- Markdown 在线编辑器
1.2 什么是 Stata dynamic tags(动态标签)?
在动态文档命令 (
dyndoc
,dyntext
) 中使用动态标签,用来定义执行某种操作,比如运行某个区域块,在文字中插入 Stata 命令的运行结果,导出图片等。
你可在 Stata 中输入 help dynamic tags
查看 dynamic tags 的具体使用说明。有两点需要注意:
- 带 / 的标签需成对出现。
- 可进一步定义标签,在后面附加属性 (attributes);形如:
<<dd_tags: attributes>>
。
可用的动态标签及相关使用方法,列在下方:
-
<<dd_version>>
定义执行命令所需的最低版本;使用时需放在单行,推荐放在文档的首行。<<dd_version: version_number>> * version_number 不是指 Stata 版本,而是命令的版本。
比如,当前
dyndoc
版本为 2, Stata 15 引入该命令, Stata 16 完善该命令。
你可输入dis c(dyndoc_version)
查看你所安装的 Stata 中该命令的相应版本。 -
<<dd_do>> 和 <</dd_do>>
执行 Stata 代码块,并可选择性地将结果显示在文档中;使用时需单行放置。<<dd_do: attribute>> block of Stata code ... <</dd_do>>
-
<<dd_display>>
在文档中显示某个 Stata 表达式的值;使用时可放在行内。<<dd_display: display_directive>> // 例子 2*1*<<dd_display:%4.2f c(pi)>> = <<dd_display:%4.2f 2*1*c(pi)>> * 输出为 2*1*3.14 = 6.28
-
<<dd_docx_display>>
只能用于putdocx textblock
命令,在文档中显示某个 Stata 表达式的值及带格式的文本;使用时可放在行内。putdocx textblock begin ... text <<dd_docx_display text_options: display_directive>> text ... putdocx textblock end // 例子 putdocx textblock begin 2*1*<<dd_docx_display bold:%4.2f c(pi)>> = <<dd_docx_display bold:%4.2f 2*1*c(pi)>> putdocx textblock end * 输出为 2*1*3.14 = 6.28 (其中 3.14 和 6.28 为粗体)。
-
<<dd_graph>>
插入图片;使用时可放在行内。<<dd_graph: attribute>>
-
<<dd_include>>
将外部文件的内容插入到文档中;使用时需放在单行。<<dd_include: filename>>
-
<<dd_ignore>> 和 <</dd_ignore>>
处理时忽略这两个标签内的代码;使用时需单行放置。 -
<<dd_skip_if>>, <<dd_skip_else>> 和 <<dd_skip_end>>
按某条件显示文本;使用时需单行放置。<<dd_skip_if: Stata expression>> lines of text ... <<dd_skip_end>> * 或者 <<dd_skip_if: Stata expression>> lines of text ... <<dd_skip_else>> lines of text ... <<dd_skip_end>>
-
<<dd_remove>> 和 <</dd_remove>>
删掉这两个标签内的内容;使用时可放在行内。... <<dd_remove>>text to remove ... lines of text to remove ... text to remove ... <</dd_remove>> ...
连享会计量方法专题……
2. 命令一:dyntext
help dyntext //输出格式为 text 文本(.txt, .html, .do)
2.1 语法结构
dyntext srcfile [arguments], saving(targetfile) [options]
其中 srcfile 是包含 dynamic tags 的纯文本格式,即我们要转换的文档;targetfile 是输出的文档。srcfile 和 targetfile 的格式均为 text 文本(.txt, .html, .do)。
- 选项说明 (options)
- saving(targetfile): 指定要保存的目标文件,saving( )是必需的。
- replace: 如果目标文件已经存在,替换目标文件。
- noremove:处理时忽略<<dd_remove>> 和 <</dd_remove>>。
- nostop:运行过程中有错误时,不中断。
2.2 范例
我们先新建一个 do 文件(也可以是 .txt 或 .html),命名为 dyntext_input1,输入内容为 *----- 间的内容。
*--------------------------begin dyntext_input1.do------------------------
In this analysis, we are going to discover
the mean miles per gallon of cars in
1978!
<<dd_do>>
sysuse auto.dta, clear
quietly summarize mpg
dis r(mean)
<</dd_do>>
*--------------------------end dyntext_input1.do---------------------------
接着我们使用 dyntext
命令,转换文档,如下:
dyntext dyntext_input1.do, saving(dyntext_output1.txt) replace
我们可以通过命令 shellout
查看输出结果,也可以在当前路径直接打开 dyntext_output1.txt
。
ssc install outreg2 // 安装此命令,调用shellout命令
shellout "dyntext_output1.txt"
输出结果如下:
*--------------------------begin dyntext_output1.txt------------------------
In this analysis, we are going to discover
the mean miles per gallon of cars in
1978!
. sysuse auto.dta, clear
(1978 Automobile Data)
. quietly summarize mpg
. dis r(mean)
21.297297
*--------------------------end dyntext_output1.txt---------------------------
3. 命令二:dyndocx
help dyndoc //输出格式为 text 文本(.html, .docx)
3.1 语法结构
dyndoc srcfile [arguments] [, options]
其中 srcfile 是包含 dynamic tags 的 Markdown 格式的文档(.txt, .md, .do),即我们要转换的文档。
- 选项说明 (options)
saving(targetfile)
: 指定要保存的目标文件,saving( )不是必需的。replace
: 如果目标文件已经存在,替换目标文件。hardwrap
:用 HTML 换行符的标签 <br> 替换 Markdown 文档中的实际换行符。nomsg
:Stata 结果输出界面不再显示指向目标文件的链接信息。nostop
:运行过程中有错误时,不中断。- [*]
embedimage
:输出的 HTML 文件中插入的图像文件为 Base64 编码。 - [*]
docx
:输出 Word 文档,而不是 HTML 文件。
需要特别说明的是:继 Stata 15 后,Stata 16 对该命令进行了完善,带 [*]
的选项不适用于 Stata 15。
3.2 范例 1:输出 HTML 文件
我们先新建一个 do 文件(也可以是 .txt 或 .md),命名为 dyndoc_example,输入内容为 *----- 间的内容。
*--------------------------begin dyndoc_example.do------------------------
<<dd_version: 2>>
<<dd_include: header.txt>>
Blood pressure report
===============================================================
We use data from the Second National Health and Nutrition Examination Survey
to study the incidence of high blood pressure.
<<dd_do:quietly>>
webuse nhanes2, clear
<</dd_do>>
## Logistic regression results
We fit a logistic regression model of high blood pressure on
weight, age group, and the interaction between age group and sex.
~~~
<<dd_do>>
logistic highbp weight agegrp##sex, nopvalues vsquish
<</dd_do>>
~~~
## Interaction plot
<<dd_do:quietly>>
margins agegrp#sex
marginsplot, title(Age Group and Sex Interaction) ///
ytitle(Expected Probability of High Blood Pressure) ///
legend(ring(0) bplacement(seast) col(1))
<</dd_do>>
<<dd_graph: saving("interaction.png") replace height(400)>>
*--------------------------end dyndoc_example.do---------------------------
其中,有以下几点需要注意:
- 上述代码中,第二行 「<<dd_include: header.txt>>」语句中的 header.txt 文件是 HTML 代码,用来定义输出文件的样式 (类似于 Word 中模板文件)。你可以调整里面的 stmarkdown.css 属性来改变样式 (关于 CSS,参见 「CSS 教程 | 菜鸟教程」)。当前工作路径下必须同时包含 header.txt 和 stmarkdown.css。你可以删掉上述
<<dd_include: header.txt>>
语句后对比一下输出结果有何差异。 - === 定义报告的标题。
- ## 定义章节标题。
- <<dd_do:quietly>> 执行代码时,不显示代码和结果。
- 若用 Stata 15 运行,则需改成 <<dd_version: 1>>。
接着我们使用 dyndoc
命令对上述进行转换:
dyndoc dyndoc_example.do, replace
我们可以通过命令 shellout
查看输出结果,也可以在当前路径直接打开 dyndoc_example.html
。
ssc install outreg2 // 安装此命令,调用shellout命令
shellout "dyndoc_example.html"
输出结果如下:
注意:用不同浏览器打开,展示的结果略有差异;还可在浏览器页面查看源代码(一般单击右键可见)。
3.3 范例 2:输出 Word 文档
利用范例 1 中的输入文件,我们在 dyndoc
后添加 docx
选项,便可将输出结果保存为 Word 文档。注意:范例 2 需使用 Stata 16 及以上版本。
dyndoc dyndoc_example.do, docx replace
* 也可以用下述命令
html2docx dyndoc.html, replace
我们可以通过命令 shellout
查看输出结果,也可以在当前路径直接打开 dyndoc_example.docx
。
ssc install outreg2 // 安装此命令,调用shellout命令
shellout "dyndoc_example.docx"
输出结果如下:
3.4. 文档结构设定:用 dyndoc 写论文
我们可以使用 dyndoc
命令写论文,但是比较头疼的事情是,每次更新时都需要重新写转换文档的命令。这种情况下,我们按如下基本思路进行处理:
- 为每篇论文建立一个文件夹,比如命名为 Mypaper_2019;
- 在该文件夹里新建一个 do 文件,命名为 _Main,用来保存转换文档用的命令,比如
dyndoc dyndoc_example.do, docx replace
; - 在该文件夹里新建一个 do 文件,命名为 Body,当作论文主文档(包含实质内容,即我们要转换的文档),比如上例中的
dyndoc_example.do
文件。
这样,每次修改或更新这篇论文时,就只需在 Body.do 中修改,然后输入命令 do _Main.do
,直接运行 _Main.do 即可。
若要进一步优化,我们可以在这个文件夹里新建一些子文件夹,如 Data,Output,Figs 等,用于存储不同类型的文件。这样,就可以保证每篇论文的文件结构都很清晰。即使时隔很久后,我们也可以很顺利地修改和更新论文。
一个一般化的文件结构如下:
结语
可通过 help dyntext
和 help dyndoc
参考更多官方范例,相关数据和文件下载地址如下:
- https://www.stata-press.com/data/r15/markdown/
- https://www.stata-press.com/data/r16/reporting/
如何重复性分析、规范地报告结果是实证研究中的难点之一。 我们可以用 dyntext
和 dyndoc
直接写 dofile,并将报告正文和图表等整合,自定义输出文本,HTML 或 Word 格式的报告,即所谓的一种输入,多种输出。这在很大程度上能减少实证研究中的工作量。
相关链接
- 官方帮助文件
- 其他参考资料
- Stata Tips #7 - dyntext, dyndoc and user-written commands
- 【STATA自动化报告与可重复研究】【陈堰平】(Automated report and reproducible research in Stata)
- 【putdocx:输出结果 so easy】【李春涛】【中南财经政法大学金融学院】(putdocx makes it easy: exporting results to Word document)
- 君生我未生!Stata - 论文四表一键出
- Stata 15之Markdown——没有做不到,只有想不到!
- 本文所用文件及数据
----点此下载----
关于我们
- Stata连享会 由中山大学连玉君老师团队创办,定期分享实证分析经验。直播间 有很多视频课程,可以随时观看。
- 你的颈椎还好吗? 您将 ::连享会-主页:: 和 ::连享会-知乎专栏:: 收藏起来,以便随时在电脑上查看往期推文。
- 公众号推文分类: 计量专题 | 分类推文 | 资源工具。推文分成 内生性 | 空间计量 | 时序面板 | 结果输出 | 交乘调节 五类,主流方法介绍一目了然:DID, RDD, IV, GMM, FE, Probit 等。
- 公众号关键词搜索/回复 功能已经上线。大家可以在公众号左下角点击键盘图标,输入简要关键词,以便快速呈现历史推文,获取工具软件和数据下载。常见关键词:
课程, 直播, 视频, 客服, 模型设定, 研究设计,
stata, plus,Profile, 手册, SJ, 外部命令, profile, mata, 绘图, 编程, 数据, 可视化
DID,RDD, PSM,IV,DID, DDD, 合成控制法,内生性, 事件研究
交乘, 平方项, 缺失值, 离群值, 缩尾, R2, 乱码, 结果
Probit, Logit, tobit, MLE, GMM, DEA, Bootstrap, bs, MC, TFP
面板, 直击面板数据, 动态面板, VAR, 生存分析, 分位数
空间, 空间计量, 连老师, 直播, 爬虫, 文本, 正则, python
Markdown, Markdown幻灯片, marp, 工具, 软件, Sai2, gInk, Annotator, 手写批注
盈余管理, 特斯拉, 甲壳虫, 论文重现
易懂教程, 码云, 教程, 知乎