✨ 欢迎关注Python机器学习AI ✨
本节介绍: 基于部分线性模型的双重机器学习方法 。数据采用模拟数据,作者根据个人对机器学习的理解进行代码实现与图表输出,细节并不保证与原文一定相同,仅供参考。 详细数据和代码、文献将在稍后上传至交流群,付费成员可在交流群中获取下载。需要的朋友可关注公众文末提供的购买方式。 购买前请咨询,避免不必要的问题。
✨ 文献信息 ✨
在这段分析中,机器学习被用来估计并控制多重影响因素,从而精准计算跨境电商政策对绿色技术创新的实际影响。具体来说,机器学习模型帮助去除了控制变量对结果的影响,使得对政策效应的估计更加可靠和准确
✨ 双重机器学习信息 ✨
双重机器学习(Double Machine Learning, DML)是一种结合了机器学习和因果推断的技术,旨在从高维数据中估计 因果效应,同时避免常见的高维数据带来的过拟合问题。DML 通过两个步骤进行建模,因此得名“双重”机器学习
- 第一步:使用机器学习方法预测并去除控制变量(如混杂因素)对处理变量和结果变量的影响,得到处理变量和结果变量的残差
- 第二步:通过回归这些残差来估计因果效应,即估计处理变量(treatment)对结果变量的实际影响
双重机器学习通过去除高维数据中的非线性关系、避免过拟合,并精确控制混杂因素,从而提高因果效应估计的准确性和可靠性
✨ 基础代码 ✨
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
plt.rcParams['font.family'] = 'Times New Roman'
plt.rcParams['axes.unicode_minus'] = False
import warnings
# 忽略所有警告
warnings.filterwarnings("ignore")
path = r"2025-5-7公众号Python机器学习AI.xlsx"
df = pd.read_excel(path)
from sklearn.preprocessing import OneHotEncoder
# 划分变量
## 结果变量:目标变量,通常是我们要预测的变量。在此例中是 'gti'。
Y = df[['gti']]
## 处理变量:表示因果推断中的“处理”变量,这里是 'cbecpolicy'。
T = df[['cbecpolicy']]
## 控制变量:这些是控制模型中可能影响结果的额外因素。它们通常是一些背景变量,比如经济指标、社会因素等。
W = df[['pgdp', 'uis','fin','inet','hca','urban','ino','enr','ure','ums', 'upm','gov']]
## 记录个体与时间固定效应:假设每个个体和每个年份有固定的影响,需要通过虚拟变量来控制。
id = df[['id']] # 个体标识符
year = df[['year']] # 时间标识符,如年份
# 使用 OneHotEncoder 对 'id' 和 'year' 进行独热编码
# 独热编码将每个类别变量转换为二进制向量形式(例如:将 'id' 列的每个唯一值转换为一个新的二进制列)
id_one_hot = OneHotEncoder(sparse_output=False).fit_transform(id)
year_one_hot = OneHotEncoder(sparse_output=False).fit_transform(year)
# 将独热编码后的 'id' 和 'year' 结果与原来的控制变量 'W' 进行列堆叠
# np.column_stack 将两个矩阵按列连接。这里将控制变量和固定效应合并,形成最终的控制矩阵。
W = np.column_stack((W, year_oen_hot, id_one_hot))
# 现在 'W' 包含了原始的控制变量以及固定效应(通过独热编码后的 id 和 year)。
通过读取数据并对控制变量(如个体和年份)进行独热编码,最终构建了一个包含结果变量、处理变量、控制变量以及固定效应的特征矩阵,为后续的因果推断分析机器学习模型做准备
import statsmodels.api as sm
from sklearn.model_selection import cross_val_predict
from sklearn.linear_model import LassoCV
# 估计 T(处理变量)的残差
# 使用 LassoCV 作为基学习器来估计 T 的预测值(T_hat)
lasso_gti_model = LassoCV(random_state=1314)
T_hat_lasso_gti = cross_val_predict(lasso_gti_model, W, T.values.ravel(), cv=5) # 用训练数据 W 和 T 估计 T 的预测值
T_residual_lasso_gti = T.values.ravel() - T_hat_lasso_gti # 计算 T 的残差,残差 = 实际值 - 预测值
# 估计 Y(结果变量)的残差
# 使用 LassoCV 作为基学习器来估计 Y 的预测值(Y_hat)
Y_hat_lasso_gti = cross_val_predict(lasso_gti_model, W, Y.values.ravel(), cv=5) # 用训练数据 W 和 Y 估计 Y 的预测值
Y_residual_lasso_gti = Y.values.ravel() - Y_hat_lasso_gti # 计算 Y 的残差,残差 = 实际值 - 预测值
# 使用 T_residual_lasso_gti 和 Y_residual_lasso_gti 进行线性回归
X_lasso_gti = sm.add_constant(T_residual_lasso_gti) # 为 T_residual_lasso_gti 添加常数项,X = [1, T_residual_lasso_gti]
model_sm_lasso_gti = sm.OLS(Y_residual_lasso_gti, X_lasso_gti).fit() # 使用 OLS 进行回归分析
# 输出系数和标准误
coef_lasso_gti = model_sm_lasso_gti.params[1] # 获取 T_residual_lasso_gti 的系数
std_err_lasso_gti = model_sm_lasso_gti.bse[1] # 获取 T_residual_lasso_gti 的标准误
# 计算 95% 置信区间
conf_int_lasso_gti = model_sm_lasso_gti.conf_int(alpha=0.05)[1] # 计算置信区间
# 获取显著性(p-value)
p_value_lasso_gti = model_sm_lasso_gti.pvalues[1] # 获取 T_residual_lasso_gti 的 p-value
# 输出结果
print(f"Coefficient for T (lasso_gti): {coef_lasso_gti}") # 输出 T_residual_lasso_gti 的系数
print(f"Standard Error (lasso_gti): {std_err_lasso_gti}") # 输出 T_residual_lasso_gti 的标准误
print(f"95% Confidence Interval for T (lasso_gti): [{conf_int_lasso_gti[0]}, {conf_int_lasso_gti[1]}]") # 输出 T_residual_lasso_gti 的 95% 置信区间
print(f"P-value for T (lasso_gti): {p_value_lasso_gti}") # 输出 T_residual_lasso_gti 的 p-value
# 判断显著性
if p_value_lasso_gti < 0.05:
print("T_residual_lasso_gti is statistically significant at the 5% level.")
else:
print("T_residual_lasso_gti is not statistically significant at the 5% level.")
通过使用 LassoCV 估计处理变量和结果变量的残差,然后进行线性回归分析,计算并输出处理变量的回归系数、标准误、置信区间和显著性水平,以评估处理效应的统计显著性
Coefficient for T (lasso_gti): 2.062454300933605
Standard Error (lasso_gti): 0.1377697001367246
95% Confidence Interval for T (lasso_gti): [1.7923232761741188, 2.332585325693091]
P-value for T (lasso_gti): 6.0655847234156794e-49
T_residual_lasso_gti is statistically significant at the 5% level.
输出结果是对 T_residual_lasso_gti (处理变量残差)进行线性回归分析后的统计结果
这里使用的数据、模型和文献中的套索回归模型一致,但回归系数和标准误差与文献中的结果略有差异,这些差异较小,且计算结果落在置信区间内,因此可以接受。差异可能与模型参数、random_state 随机种子的不同设置有关,固定随机种子有助于模型复现,但不同的随机种子可能会导致模型结果存在细微差别,此外,模型的其他参数也可能影响结果
from sklearn.linear_model import ElasticNetCV
# 估计 T(处理变量)的残差
# 使用 ElasticNetCV 作为基学习器来估计 T 的预测值(T_hat)
elastic_net_gti_model = ElasticNetCV(random_state=1314)
T_hat_elastic_net_gti = cross_val_predict(elastic_net_gti_model, W, T.values.ravel(), cv=5) # 用训练数据 W 和 T 估计 T 的预测值
T_residual_elastic_net_gti = T.values.ravel() - T_hat_elastic_net_gti # 计算 T 的残差,残差 = 实际值 - 预测值
# 估计 Y(结果变量)的残差
# 使用 ElasticNetCV 作为基学习器来估计 Y 的预测值(Y_hat)
Y_hat_elastic_net_gti = cross_val_predict(elastic_net_gti_model, W, Y.values.ravel(), cv=5) # 用训练数据 W 和 Y 估计 Y 的预测值
Y_residual_elastic_net_gti = Y.values.ravel() - Y_hat_elastic_net_gti # 计算 Y 的残差,残差 = 实际值 - 预测值
# 使用 T_residual_elastic_net_gti 和 Y_residual_elastic_net_gti 进行线性回归
X_elastic_net_gti = sm.add_constant(T_residual_elastic_net_gti) # 为 T_residual_elastic_net_gti 添加常数项,X = [1, T_residual_elastic_net_gti]
model_sm_elastic_net_gti = sm.OLS(Y_residual_elastic_net_gti, X_elastic_net_gti).fit() # 使用 OLS 进行回归分析
# 输出系数和标准误
coef_elastic_net_gti = model_sm_elastic_net_gti.params[1] # 获取 T_residual_elastic_net_gti 的系数
std_err_elastic_net_gti = model_sm_elastic_net_gti.bse[1] # 获取 T_residual_elastic_net_gti 的标准误
# 计算 95% 置信区间
conf_int_elastic_net_gti = model_sm_elastic_net_gti.conf_int(alpha=0.05)[1] # 计算置信区间
# 获取显著性(p-value)
p_value_elastic_net_gti = model_sm_elastic_net_gti.pvalues[1] # 获取 T_residual_elastic_net_gti 的 p-value
# 输出结果
print(f"Coefficient for T (elastic_net_gti): {coef_elastic_net_gti}") # 输出 T_residual_elastic_net_gti 的系数
print(f"Standard Error (elastic_net_gti): {std_err_elastic_net_gti}") # 输出 T_residual_elastic_net_gti 的标准误
print(f"95% Confidence Interval for T (elastic_net_gti): [{conf_int_elastic_net_gti[0]}, {conf_int_elastic_net_gti[1]}]") # 输出 T_residual_elastic_net_gti 的 95% 置信区间
print(f"P-value for T (elastic_net_gti): {p_value_elastic_net_gti}") # 输出 T_residual_elastic_net_gti 的 p-value
# 判断显著性
if p_value_elastic_net_gti < 0.05:
print("T_residual_elastic_net_gti is statistically significant at the 5% level.")
else:
print("T_residual_elastic_net_gti is not statistically significant at the 5% level.")
将模型更换为 弹性网络回归(ElasticNetCV),通过该模型估计处理变量和结果变量的残差,并使用线性回归分析残差,计算回归系数、标准误、置信区间和显著性,以评估处理效应的统计显著性
Coefficient for T (elastic_net_gti): 2.069372606511402
Standard Error (elastic_net_gti): 0.13816721583430117
95% Confidence Interval for T (elastic_net_gti): [1.798462155487376, 2.340283057535428]
P-value for T (elastic_net_gti): 5.498915977783063e-49
T_residual_elastic_net_gti is statistically significant at the 5% level.
文献中的回归系数为 2.093 ,这里我们计算的回归系数为 2.069,文献中的标准误为 0.197,这里计算的标准误为 0.138,文献中的置信区间为 [1.792, 2.332],这里计算的置信区间为 [1.798, 2.340],回归结果显著性非常高,尽管回归系数和标准误差在数值上有轻微差异,但这些差异较小,并且计算结果落在置信区间内,因此可以认为两者的结果非常一致,差距并不大。可能的差异来源包括数据样本、随机种子、交叉验证方法等因素
Y = df[['gti1']]
T = df[['cbecpolicy']]
W = df[['pgdp', 'uis','fin','inet','hca','urban','ino','enr','upm','gov','ure','ums']]
id = df[['id']]
year = df[['year']]
id_one_hot = OneHotEncoder(sparse_output=False).fit_transform(id)
year_one_hot = OneHotEncoder(sparse_output=False).fit_transform(year)
W = np.column_stack((W, year_one_hot, id_one_hot))
# 估计 T(处理变量)的残差
# 使用 LassoCV 作为基学习器来估计 T 的预测值(T_hat)
lasso_gti1_model = LassoCV(random_state=1314)
T_hat_lasso_gti1 = cross_val_predict(lasso_gti1_model, W, T.values.ravel(), cv=5) # 用训练数据 W 和 T 估计 T 的预测值
T_residual_lasso_gti1 = T.values.ravel() - T_hat_lasso_gti1 # 计算 T 的残差,残差 = 实际值 - 预测值
# 估计 Y(结果变量)的残差
# 使用 LassoCV 作为基学习器来估计 Y 的预测值(Y_hat)
Y_hat_lasso_gti1 = cross_val_predict(lasso_gti1_model, W, df['gti1'].values.ravel(), cv=5) # 用训练数据 W 和 gti1 估计 Y 的预测值
Y_residual_lasso_gti1 = df['gti1'].values.ravel() - Y_hat_lasso_gti1 # 计算 Y 的残差,残差 = 实际值 - 预测值
# 使用 T_residual_lasso_gti1 和 Y_residual_lasso_gti1 进行线性回归
X_lasso_gti1 = sm.add_constant(T_residual_lasso_gti1) # 为 T_residual_lasso_gti1 添加常数项,X = [1, T_residual_lasso_gti1]
model_sm_lasso_gti1 = sm.OLS(Y_residual_lasso_gti1, X_lasso_gti1).fit() # 使用 OLS 进行回归分析
# 输出系数和标准误
coef_lasso_gti1 = model_sm_lasso_gti1.params[1] # 获取 T_residual_lasso_gti1 的系数
std_err_lasso_gti1 = model_sm_lasso_gti1.bse[1] # 获取 T_residual_lasso_gti1 的标准误
# 计算 95% 置信区间
conf_int_lasso_gti1 = model_sm_lasso_gti1.conf_int(alpha=0.05)[1] # 计算置信区间
# 获取显著性(p-value)
p_value_lasso_gti1 = model_sm_lasso_gti1.pvalues[1] # 获取 T_residual_lasso_gti1 的 p-value
# 输出结果
print(f"Coefficient for T (lasso_gti1): {coef_lasso_gti1}") # 输出 T_residual_lasso_gti1 的系数
print(f"Standard Error (lasso_gti1): {std_err_lasso_gti1}") # 输出 T_residual_lasso_gti1 的标准误
print(f"95% Confidence Interval for T (lasso_gti1): [{conf_int_lasso_gti1[0]}, {conf_int_lasso_gti1[1]}]") # 输出 T_residual_lasso_gti1 的 95% 置信区间
print(f"P-value for T (lasso_gti1): {p_value_lasso_gti1}") # 输出 T_residual_lasso_gti1 的 p-value
# 判断显著性
if p_value_lasso_gti1 < 0.05:
print("T_residual_lasso_gti1 is statistically significant at the 5% level.")
else:
print("T_residual_lasso_gti1 is not statistically significant at the 5% level.")
这里和文献一样改变结果变量对 gti1 进行套索回归,估计处理变量 cbecpolicy 对结果变量 gti1 的影响,计算相关的回归系数、标准误、置信区间和显著性检验,并得出了显著性的判断
Coefficient for T (lasso_gti1): 0.956482271563501
Standard Error (lasso_gti1): 0.07466070132328512
95% Confidence Interval for T (lasso_gti1): [0.8100917971870178, 1.102872745939984]
P-value for T (lasso_gti1): 1.2345658506703944e-36
T_residual_lasso_gti1 is statistically significant at the 5% level.
可以发现,虽然我们代码计算的回归系数为 0.956 ,而文献中的回归系数为 0.980 ,两者略有差异,但差距较小,且都在统计上显著,都落在置信区间内,因此可以认为结果是一致的,差异可能由随机种子或其他模型参数引起
Coefficient for T (lasso_gti2): 0.0008114700206588038
Standard Error (lasso_gti2): 0.00024410972427414354
95% Confidence Interval for T (lasso_gti2): [0.0003328334996640667, 0.0012901065416535409]
P-value for T (lasso_gti2): 0.0008972144619989594
T_residual_lasso_gti2 is statistically significant at the 5% level.
最后同样对 gti2 进行计算,结果显示回归系数为 0.000811,标准误为 0.000244,而文献中的回归系数为 0.001,标准误为 0.000,二者差异较小,且都在统计上显著,因此可以认为两者结果一致,差异可能由随机种子或其他模型参数导致
这里通过双重机器学习的原理一步一步实现了使用机器学习方法预测并去除控制变量(如混杂因素)对处理变量和结果变量的影响,从而得到处理变量和结果变量的残差。通过回归这些残差,最终估计了处理变量(treatment)对结果变量的实际影响。虽然手动实现了这一过程,但也有相关库如 econml
提供了更为方便快捷的双重机器学习实现,下期将对该库的使用进行简单讲解,以便快速达到这种效果方便初学者使用
✨ 该文章案例 ✨
在上传至交流群的文件中,像往期文章一样,将对案例进行逐步分析,确保读者能够达到最佳的学习效果。内容都经过详细解读,帮助读者深入理解模型的实现过程和数据分析步骤,从而最大化学习成果。
同时,结合提供的免费AI聚合网站进行学习,能够让读者在理论与实践之间实现融会贯通,更加全面地掌握核心概念。
✨ 购买介绍 ✨
本节介绍到此结束,有需要学习数据分析和Python机器学习相关的朋友欢迎到淘宝店铺:Python机器学习AI,或添加作者微信deep_ML联系,购买作者的公众号合集。截至目前为止,合集已包含近300多篇文章,购买合集的同时,还将提供免费稳定的AI大模型使用,包括但不限于ChatGPT、Deepseek、Claude等。
更新的内容包含数据、代码、注释和参考资料。 作者仅分享案例项目,不提供额外的答疑服务。项目中将提供详细的代码注释和丰富的解读,帮助您理解每个步骤 。 购买前请咨询,避免不必要的问题。
✨ 群友反馈 ✨
✨ 淘宝店铺 ✨
请大家打开淘宝扫描上方的二维码,进入店铺,获取更多Python机器学习和AI相关的内容,或者添加作者微信deep_ML联系 避免淘宝客服漏掉信息 ,希望能为您的学习之路提供帮助!
✨ 免费赠书 ✨
支持知识分享,畅享学习乐趣!特别感谢清华大学出版社 对本次赠书活动的鼎力支持!即日起,只需点赞、推荐、转发 此文章,作者将从后台随机抽取一位幸运儿,免费包邮赠送清华出版社提供的《Transformer深度解析与NLP应用开发》这本精彩书籍📚!
💡 赶快参与,一键三连,说不定你就是那位幸运读者哦!
往期推荐
Frontiers in Oncology:利用生存机器学习RSF模型预测患者预后模拟实现
期刊配图:通过SHAP组图解读模型探索不同类型特征和分组对模型的影响
机器学习在临床数据分析中的应用:从数据预处理到Web应用实现的完整流程教学
Psychiatry Research基于SHAP可解释性的机器学习模型构建与评估:混淆矩阵、ROC曲线、DCA与校准曲线分析
nature communications:基于Light GBM与随机森林结合的多模型特征选择方法
如果你对类似于这样的文章感兴趣。
欢迎关注、点赞、转发~
个人观点,仅供参考