Causal Forest (grf) 因果森林是什么?
Causal Forest 回答的是处理效应是否因个体特征不同而不同。它不是为了预测 Y 最准,而是估计条件平均处理效应 CATE。
先用一句话理解
把因果森林想成把样本切成很多相似的小组,看看政策对哪些人更有用、对哪些人没用。森林负责寻找异质性模式,但前提仍然是处理分配在控制变量后足够可比。
什么时候用
| 判断项 | 教科书式判断 |
|---|---|
| 适合用在 | 关注异质处理效应,并有较多协变量描述个体差异。 |
| 先不要用在 | 没有可信处理识别,或样本太小却想让森林发现复杂异质性。 |
| 最关键的前提 | 仍需要 unconfoundedness、overlap 或实验设计支持。 |
| 读表顺序 | 先看 ATE,再看 CATE 分布、重要特征和分组效应。 |
| 论文表述边界 | Causal Forest 发现异质性线索,不自动解释机制。 |
把它和相近方法分清楚
| 容易混淆的对象 | 怎么区分 | 初学者记法 |
|---|---|---|
| 异质性交互项 | 预先指定某个分组。 | 结构透明但有限。 |
| Causal Forest | 数据驱动寻找异质性。 | 灵活但更依赖诊断。 |
| 预测随机森林 | 预测 Y。 | 不直接估计处理效应。 |
核心直觉和模型公式
条件平均处理效应
Causal Forest 的目标是估计:
\[\tau(x)=E[Y(1)-Y(0)\mid X=x]\]
tau(x) 表示特征为 x 的个体的处理效应,而不是全样本一个平均数。
公式里的符号怎么读
| 符号 | 含义 | 在本页怎么理解 |
|---|---|---|
| Y(1) | 处理状态潜在结果 | 个体接受处理时的结果。 |
| Y(0) | 未处理状态潜在结果 | 个体不接受处理时的结果。 |
| X=x | 个体特征 | 用于刻画异质性的协变量。 |
| τ(x) | CATE | 条件平均处理效应。 |
| overlap | 重叠支持 | 同类个体中既有处理组也有对照组。 |
专业使用口径
专业因果森林报告要避免把黑箱异质性写成确定机制。
| 口径 | 专业写法 |
|---|---|
| ATE 基线 | 先报告平均处理效应。 |
| CATE 分布 | 展示处理效应在样本中的分布。 |
| 特征重要性 | 说明哪些变量主要驱动异质性。 |
| 验证分组 | 把高/低 CATE 组做透明分组对照。 |
一步一步做:从问题到结果的五步
| 步骤 | 这一页具体做什么 | 做到什么程度才算读懂 |
|---|---|---|
| 1. 明确处理变量 | D 必须有可解释的处理含义。 | 不能只是任意预测特征。 |
| 2. 检查可比性 | 控制 X 后处理和对照是否有重叠。 | 没有 overlap 无法估个体效应。 |
| 3. 估计 CATE | 森林寻找不同 X 下的效应。 | 异质性是目标。 |
| 4. 汇总异质性 | 看分布、分位数组和重要特征。 | 不要只报一张变量重要性图。 |
| 5. 做外部解释 | 结合理论解释哪些组效应更强。 | 森林本身不提供机制。 |
结果怎么读:先读口径,再读数字
本页案例读表时,先记住这个口径:全样本 ATE proxy 是 0.0032,民营企业 CATE 是 0.0035,国有企业 CATE 是 0.0033。
| 读表顺序 | 本页怎么读 | 不要这样读 |
|---|---|---|
| 先看 ATE | 平均效应是否存在。 | 异质性应建立在主问题上。 |
| 再看 CATE 分布 | 效应差异有多大。 | 分布比单点更重要。 |
| 然后看 overlap | 高低 CATE 组是否可比。 | 支持集不足会误导。 |
| 最后看解释 | 哪些特征驱动异质性。 | 解释要回到理论。 |
初学者最容易错在哪里
| 误读 | 为什么错 |
|---|---|
| 把预测森林当因果森林 | 错。目标函数不同。 |
| 没有识别假设仍解释 CATE | 错。森林不创造反事实。 |
| 只看变量重要性 | 不够。要看效应大小和不确定性。 |
| 把异质性当机制 | 过强。异质性说明谁更受影响,不说明为什么。 |
先看这个案例的结论
- 全样本 ATE proxy 是 0.0032,民营企业 CATE 是 0.0035,国有企业 CATE 是 0.0033。
- CATE spread 是 0.0019;因果森林页真正要看的不是平均系数,而是哪些企业的效应更强。
- 这里用同一份案例数据做教学近似;正式生产代码建议用 R 的 grf 输出 ATE、CATE 分布和变量重要性。
变量要求和案例口径
| 字段 | 口径 |
|---|---|
| 数据 | CSMAR 风格 A 股企业创新面板 |
| 原始样本 | 196 家上市公司,2015-2020 年,约 1200 个公司-年观测;各方法有效样本以本页输出表 N 为准 |
| 因变量 | patent_count;回归页通常使用 ln(1 + patent_count) |
| 核心解释变量 | dfi_index,数字普惠金融指数;部分案例输出展示的是标准化后的 dfi_index |
| 控制变量 | roa、lev、size、growth、cashflow、tobinq、top1、dual、board、indep、soe、age |
| 输出文件 | causal_forest_results.csv |
| 角色要求 | 因变量、核心解释变量 |
| 依赖包 | grf |
实际代码
下面是本页案例里的最小 Stata 代码。它的作用是帮助你看清变量怎么进入模型、结果文件怎么生成,而不是要求你在网页里手动运行。
import delimited "$DATA_PATH", clear varnames(1) encoding(UTF-8)
gen ln_patent1 = ln(1 + patent_count)
egen firm_id = group(stkcd)
xtset firm_id year
global y ln_patent1
global count_y patent_count
global x dfi_index
global controls roa lev size growth cashflow tobinq top1 dual board indep soe age
gen post = year >= 2018
bysort firm_id: egen pre_dfi = mean(cond(year < 2018, dfi_index, .))
quietly summarize pre_dfi, detail
gen treat = pre_dfi >= r(p50)
gen did = treat * post
gen high_patent = patent_count > 2
gen running_dfi = dfi_index - 260
gen rdd_treat = running_dfi >= 0
* R grf version is preferred for production:
* causal_forest(X, Y, W); average_treatment_effect(forest)
reg $y c.$x##i.soe $controls i.year, vce(cluster firm_id)
export delimited using "$JOB_DIR/causal_forest_results.csv", replace
实际输出表
这张表是本方法页配套案例的输出结果,用来把前面的公式、变量口径和代码对应到实际数字。
| 指标 | 数值 | 解释 |
|---|---|---|
| 样本 | 1200 obs / 196 firms / 2015-2020 | 来自共用案例 CSV |
| 因变量 | ln(1 + patent_count) | 企业创新产出 |
| 核心解释变量 | dfi_index | 数字普惠金融指数 |
| 输出文件 | causal_forest_results.csv | empirical-wizard 对应方法产物 |
| ATE proxy | 0.0032 | 全样本 DFI 平均效应,作为 causal forest 的基准对照 |
| CATE: 民营企业 | 0.0035 | 用子样本斜率近似展示异质处理效应 |
| CATE: 国有企业 | 0.0033 | 正式因果森林会用 grf 估计个体层 CATE |
| CATE spread | 0.0019 | 不同组别效应差距;这才是因果森林页要看的量 |
案例图
这是一张由同一份案例数据生成的页面内诊断图。

论文里怎么写
本文在共用企业面板样本上报告Causal Forest (grf) 因果森林,核心输出见 causal_forest_results.csv。结果解释时同时关注样本口径、变量构造、系数方向、标准误和适用前提,避免只凭单个 p 值完成方法选择。
检查清单
- 先明确处理变量和协变量集合,因果森林不是普通预测随机森林。
- 重点读 CATE 分布和变量重要性,而不是只看平均处理效应。
- 发现异质性后要回到理论解释,不能把算法分组直接当机制。