因果推断之微软开源的dowhy使用学习
创始人
2024-06-02 17:52:59
0

本文参考微软dowhy官网文档,并参考相关博客进行整理而来,官方地址:https://github.com/py-why/dowhy

0x01. 概述

因果推理是基于观察数据进行反事实估计,分析干预与结果之间的因果关系。

DoWhy是微软发布的端到端因果推断Python库,主要特点是:

  • 基于一定经验假设的基础上,将问题转化为因果图,验证假设。
  • 提供因果推断的接口,整合了两种因果框架。
  • DoWhy支持对后门、前门和工具的平均因果效应的估计,自动验证结果的准确性、鲁棒性较高。

DoWhy 的整个因果推断过程可以划分为四大步骤:

  1. 「建模」(model): 利用假设(先验知识)对因果推断问题建模。
  2. 「识别」(identify): 在假设(模型)下识别因果效应的表达式(因果估计量)。
  3. 「估计」(estimate): 使用统计方法对表达式进行估计。
  4. 「反驳」(refute): 使用各种鲁棒性检查来验证估计的正确性。

先看一张流程图:

在这里插入图片描述
对四个流程进行解释说明:

0x01_1. 建模

为每个问题创建一个因果图模型,以保证因果假设的明确性。该因果图不需要是完整的,你可以只提供部分图,来表示某些变量的先验知识(即指定其类型),DoWhy 支持自动将剩余的变量视为潜在的混杂因子

目前,DoWhy支持以下形式的因果假设:

  • 「图」(Graph): 提供 gml 或 dot 形式的因果图,具体可以是文件或字符串格式
  • 命名变量集合」(Named variable sets): 直接提供变量的类型,包括 混杂因子(common causes / cofounders)工具变量(instrumental variables)结果修改变量(effect modifiers)、**前门变量(front-door variables)**等。

0x01_2. 识别

基于构建的因果图,DoWhy 会基于所有可能的方式来识别因果效应。识别方式包含:

  • 后门准则(Back-door criterion)
  • 前门准则(Front-door criterion)
  • 工具变量(Instrumental Variables)
  • 中介-直接或间接结果识别(Mediation-Direct and indirect effect identification)

0x01_3. 估计

  • 基于估计干预分配的方法(Methods based on estimating the treatment assignment)

    • 基于倾向的分层(Propensity-based Stratification)
    • 倾向得分匹配(Propensity Score Matching)
    • 逆向倾向加权(Inverse Propensity Weighting)
  • 基于估计结果模型的方法(Methods based on estimating the outcome model)

    • 线性回归(Linear Regression)
    • 广义线性模型(Generalized Linear Models)
  • 基于工具变量等式的方法(Methods based on the instrumental variable equation)

    • 二元工具/Wald 估计器(Binary Instrument/Wald Estimator)
    • 两阶段最小二乘法(Two-stage least squares)
    • 非连续回归(Regression discontinuity)
  • 基于前门准则和一般中介的方法(Methods for front-door criterion and general mediation)

    • 两层线性回归(Two-stage linear regression)

0x01_4. 反驳

DoWhy 支持多种反驳方法来验证估计的正确性,具体列表如下:

  • 添加随机混杂因子:添加一个随机变量作为混杂因子后估计因果效应是否会改变(期望结果:不会)
  • 安慰剂干预:将真实干预变量替换为独立随机变量后因果效应是否会改变(期望结果:因果效应归零)
  • 虚拟结果:将真实结果变量替换为独立随机变量后因果效应是否会改变(期望结果:因果效应归零)
  • 模拟结果:将数据集替换为基于接近给定数据集数据生成过程的方式模拟生成的数据集后因果效应是否会改变(期望结果:与数据生成过程的效应参数相匹配)
  • 添加未观测混杂因子:添加一个额外的与干预和结果相关的混杂因子后因果效应的敏感性(期望结果:不过度敏感)
  • 数据子集验证:将给定数据集替换为一个随机子集后因果效应是否会改变(期望结果:不会)
  • 自助验证:将给定数据集替换为同一数据集的自助样本后因果效应是否会改变(期望结果:不会)

0x02. 入门案例学习

依旧以微软官方文档为主进行学习,其中包含基础案例和酒店住宿分析问题。

0x02_1. 安装环境

windows环境下,请在python3.8以上的环境下进行安装。

pip install dowhy

conda install -c conda-forge dowhy

其次是需要安装pygraphviz,windows具体安装教程参考:传送门

0x02_1. 导包加载数据

from dowhy import CausalModel
import dowhy.datasets# Load some sample data
data = dowhy.datasets.linear_dataset(beta=10, # 因果效应值num_common_causes=5, # 混杂因子,用w表示,作用于干预变量和结果变量num_instruments=2, # 工具变量,用 Z 表示,作用于干预变量(间接影响结果)num_samples=10000,  # 样本数量treatment_is_binary=True) # 干预为二元变量,用 v 表示
df = data["df"] # DoWhy 使用 pandas 的 dataframe 来载入数据
print(df.head(5))

结果输出如下:

    Z0	   Z1			W0			W1			W2			W3			W4		 v0			y
0	0.0	0.478130	0.313025	0.274645	1.794765	-1.551661	1.250724	True	17.033979
1	0.0	0.546833	-0.197845	-2.404349	1.120160	-1.011344	0.812087	True	3.074740
2	0.0	0.874135	1.047078	-0.056460	0.440413	-0.067349	0.970203	True	15.530070
3	0.0	0.913483	0.934282	-1.180582	0.498135	-1.079074	-1.659924	True	5.046809
4	0.0	0.366969	-0.364818	0.630643	-0.330043	0.572139	-0.433893	True	11.004590

输出 gml_graph,内容一致只是表达形式不同,查看一下构建的,代码如下:

print(data["dot_graph"])

结果如下:

digraph {v0->y;W0-> v0; W1-> v0; W2-> v0; W3-> v0; W4-> v0;Z0-> v0; Z1-> v0;W0-> y; W1-> y; W2-> y; W3-> y; W4-> y;}

0x02_2. 执行因果推断

0x02_2_1. 建模

model=CausalModel(data = df,treatment=data["treatment_name"],outcome=data["outcome_name"],graph=data["gml_graph"])
model.view_model() # 对构建的因果图可视化
from IPython.display import Image, display
display(Image(filename="causal_model.png"))

执行代码后,结果如下:

在这里插入图片描述
上图包含了数据中给定的先验知识,我们可以利用这张图来识别因果效应(从因果估计量到概率表达式)并进行估计。

0x02_2_2. 识别

可以脱离于数据,仅根据图进行识别,其给出的结果是一个用于计算的「表达式」。具体的代码如下:

identified_estimand = model.identify_effect()
print(identified_estimand)

输出结果如下:

Estimand type: EstimandType.NONPARAMETRIC_ATE### Estimand : 1
Estimand name: backdoor
Estimand expression:d                       
─────(E[y|W1,W0,W4,W2,W3])
d[v₀]                     
Estimand assumption 1, Unconfoundedness: If U→{v0} and U→y then P(y|v0,W1,W0,W4,W2,W3,U) = P(y|v0,W1,W0,W4,W2,W3)### Estimand : 2
Estimand name: iv
Estimand expression:⎡                              -1⎤⎢    d        ⎛    d          ⎞  ⎥
E⎢─────────(y)⋅⎜─────────([v₀])⎟  ⎥⎣d[Z₁  Z₀]    ⎝d[Z₁  Z₀]      ⎠  ⎦
Estimand assumption 1, As-if-random: If U→→y then ¬(U →→{Z1,Z0})
Estimand assumption 2, Exclusion: If we remove {Z1,Z0}→{v0}, then ¬({Z1,Z0}→y)### Estimand : 3
Estimand name: frontdoor
No such variable(s) found!

0x02_2_3. 估计

estimate = model.estimate_effect(identified_estimand,method_name="backdoor.propensity_score_stratification")
print(estimate)

输出结果如下:

*** Causal Estimate ***## Identified estimand
Estimand type: EstimandType.NONPARAMETRIC_ATE### Estimand : 1
Estimand name: backdoor
Estimand expression:d                       
─────(E[y|W1,W0,W4,W2,W3])
d[v₀]                     
Estimand assumption 1, Unconfoundedness: If U→{v0} and U→y then P(y|v0,W1,W0,W4,W2,W3,U) = P(y|v0,W1,W0,W4,W2,W3)## Realized estimand
b: y~v0+W1+W0+W4+W2+W3
Target units: ate## Estimate
Mean value: 9.942351552191596

可以通过 target_units 参数来选择因果效应分析的群体,如 ate(群体层面)、att(干预组)、ate(对照组)。也可以指定结果修改变量来分析不同变量对结果的影响。

0x02_2_4. 反驳

反驳阶段参考其他博客内容进行实验,采用多种方式验证。

添加一个随机的混杂因子变量

res_random=model.refute_estimate(identified_estimand, estimate, method_name="random_common_cause")
print(res_random)

输出结果如下:

Refute: Add a random common cause
Estimated effect:9.942351552191596
New effect:9.942351552191594
p value:2.0

添加一个未观测的混杂因子变量

res_unobserved=model.refute_estimate(identified_estimand, estimate, method_name="add_unobserved_common_cause", confounders_effect_on_treatment="binary_flip", confounders_effect_on_outcome="linear", effect_strength_on_treatment=0.01, effect_strength_on_outcome=0.02)
print(res_unobserved)

输出结果如下:

Refute: Add an Unobserved Common Cause
Estimated effect:9.942351552191596
New effect:9.451291104262298

用随机变量代替干预

res_placebo=model.refute_estimate(identified_estimand, estimate, method_name="placebo_treatment_refuter", placebo_type="permute")
print(res_placebo)

输出结果如下:

Refute: Use a Placebo Treatment
Estimated effect:9.942351552191596
New effect:-0.014386044006960131
p value:0.8999999999999999

移除数据的一个随机子集

res_subset=model.refute_estimate(identified_estimand, estimate, method_name="data_subset_refuter", subset_fraction=0.9)
print(res_subset)

输出结果如下:

Refute: Use a subset of data
Estimated effect:9.942351552191596
New effect:9.934071804782558
p value:0.8600000000000001

我们可以通过 random_seed 参数来保证结果的可重现性。

0x03. 总结

跟着官网的实验跑一趟,对该分析工具认识加深,特别是工具安装和使用,分析的结果可呈现。对该工具的认识也加深不少。

参考链接:

  1. 微软DoWhy官方教程
  2. 因果推断框架 DoWhy 入门

相关内容

热门资讯

歌颂母亲的诗歌 歌颂母亲的诗歌(15篇)  无论在学习、工作或是生活中,许多人都接触过一些比较经典的诗歌吧,诗歌具有...
诗词之源早于《诗经》 诗词之源早于《诗经》  大量史料说明,中国诗歌的星宿之海应上溯一千年,虞舜时代的《卿云歌》和《南风歌...
在我最想你的时候爱情诗歌 在我最想你的时候爱情诗歌  在我最想你的时候  默然夕拾  夜深了  几乎绣花针掉到地上  都能发出...
谢灵运山水诗对李白的创作影响 谢灵运山水诗对李白的创作影响  东晋诗人谢灵运,作为中国古典诗歌山水诗派的开创者之一,在晋宋之交,为...
永远的守巢人诗歌_歌颂老师   又到毕业季,又有不少的孩子即将离开那个呵护了他们三年的小乐园,开始第一次学会和朋友们说再见。下面...
小学生抗疫情诗歌 小学生抗疫情诗歌  无论是身处学校还是步入社会,大家一定没少看到经典的诗歌吧,诗歌语言言简义丰,具有...
忘不掉你的承诺诗歌 忘不掉你的承诺诗歌  当自己心中的那个他走了之后,  让人最难忘记的是“记忆”  因为,  那一段记...
你是我心中永远的痛爱情诗歌 你是我心中永远的痛爱情诗歌  你我曾经  肩并肩、手牵着手徜徉在花丛中  一起观赏人间的四季美景  ...
爱情的诗歌 有关爱情的诗歌  在平时的学习、工作或生活中,大家都看到过许多经典的诗歌吧,诗歌是按照一定的音节、韵...
适合过年听的欢快的歌曲 适合过年听的欢快的歌曲  过年期间都是一个很喜庆的时间,很多店铺商场都开始放一些音乐去吸引客人或者说...
醉生梦死诗歌 醉生梦死诗歌醉生梦死诗歌1  禁果的滋味  苦涩而甜蜜  人生第一次爱过  不知不觉已成悲伤之人  ...
《雨说》诗歌 《雨说》诗歌  在平日的学习、工作和生活里,许多人都接触过一些比较经典的诗歌吧,诗歌饱含丰富的感情和...
蜗行诗歌 蜗行诗歌  在生活、工作和学习中,大家总免不了要接触或使用诗歌吧,诗歌在形式上,不是以句子为单位,而...
国庆节的诗歌 关于国庆节的诗歌再过几天就是十月一号的国庆节了,自古以来,吟诗作赋是文人对节日的表达感情方式之一。下...
歌颂伟大的母亲党成立100周... 弹指间,2021年来了,我们伟大的母亲中国共产党也走过了100年,那歌颂伟大的母亲中国共产党成立10...
欧阳修的醉翁亭记 欧阳修的醉翁亭记  《醉翁亭记》不仅是一首千古传诵的游记,散文中饶有诗情画意,别具清丽格调,是一篇具...
关于中秋节的诗歌大全 关于中秋节的诗歌大全,小编为你推荐下文,希望可以帮助到你。欢迎你的阅读参考。1、《中秋》唐·李朴皓魄...
《落日怅望》诗歌鉴赏 《落日怅望》诗歌鉴赏  落日怅望  马戴  孤云与归鸟,千里片时间。  念我何留滞,辞家久未还。  ...
小学画课文原文 小学画课文原文  画为初唐诗人王维所做的一首五言绝句。下面就随小编一起去阅读小学画古诗原文,相信能带...
诗歌赏析:《六月的雨》 诗歌赏析:《六月的雨》  在平日的学习、工作和生活里,大家都经常接触到诗歌吧,诗歌是一种抒情言志的文...