前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >提高回归模型精度的技巧总结

提高回归模型精度的技巧总结

作者头像
deephub
发布于 2021-07-01 03:06:54
发布于 2021-07-01 03:06:54
2K00
代码可运行
举报
文章被收录于专栏:DeepHub IMBADeepHub IMBA
运行总次数:0
代码可运行

在这篇文章中,我们将看到如何处理回归问题,以及如何通过使用特征转换、特征工程、聚类、增强算法等概念来提高机器学习模型的准确性。

数据科学是一个迭代的过程,只有经过反复的实验,我们才能得到最适合我们需求的模型/解决方案。

让我们通过一个例子来关注上面的每个阶段。我有一个健康保险数据集(CSV文件),其中包含保险费用、年龄、性别、BMI等客户信息。我们必须根据数据集中的这些参数预测保险费用。这是一个回归问题,因为我们的目标变量——费用/保险成本——是数字的。

让我们从加载数据集和探索属性开始(EDA -探索性数据分析)

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 #Load csv into a dataframe
 df=pd.read_csv('insurance_data.csv')
 df.head(3)#Get the number of rows and columns
 print(f'Dataset size: {df.shape}')
 (1338,7)

数据集有1338条记录和6个特性。吸烟者、性别和地区是分类变量,而年龄、BMI和儿童是数字变量。

零/缺失值处理

让我们检查数据集中缺失值的比例:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 df.isnull().sum().sort_values(ascending=False)/df.shape[0]

年龄和BMI有一些零值——虽然很少。我们将处理这些缺失的数据,然后开始数据分析。Sklearn的SimpleImputer允许您根据各自列中的平均值/中值/最频繁值替换缺失的值。在本例中,我使用中值来填充空值。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 #Instantiate SimpleImputer 
 si=SimpleImputer(missing_values = np.nan, strategy="median")
 si.fit(df[[’age’, 'bmi’]])
   
 #Filling missing data with median
 df[[’age’, 'bmi’]] = si.transform(df[[’age’, 'bmi’]])

数据可视化

现在我们的数据是干净的,我们将通过可视化和地图来分析数据。一个简单的海产配对可以给我们很多启示!

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 sns.pairplot(data=df, diag_kind='kde')

我们看到了什么?

收费和儿童被扭曲了。

年龄与收费呈正相关。

BMI服从正态分布!?

Seaborn的箱线图和计数图可以用来揭示分类变量对收费的影响。

根据上述图的观察:

男性和女性的数量几乎相等,男性和女性的平均收费中位数也相同,但男性的收费范围更高。

吸烟者的保险费用相对较高。

有2-3个孩子的人收费最高

这4个地区的客户几乎是平均分布的,而且他们的费用几乎相同。

女性吸烟者的百分比低于男性吸烟者的百分比。

因此,我们可以得出结论,“吸烟者”对保险费用有相当大的影响,而性别的影响最小。

让我们创建一个热图来理解特征(年龄、BMI和儿童)之间的相关性。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 sns.heatmap(df[['age', 'bmi', 'children', 'charges']].corr(), cmap='Blues', annot=True)
 plt.show()

我们看到年龄和体重指数与收费有平均相关性。

现在,我们将逐一介绍模型准备和模型开发的步骤。

特征编码

在这个步骤中,我们将分类变量——吸烟者、性别和地区——转换为数字格式(0、1、2、3等),因为大多数算法不能处理非数字数据。这个过程叫做编码,有很多方法可以做到这一点:

LabelEncoding—将分类值表示为数字(例如,带有意大利、印度、美国、英国等值的Region可以表示为1、2、3、4)

OrdinalEncoding——用于将基于排名的分类数据值表示为数字。(例如用1,2,3表示高、中、低)

独热编码-将类别数据表示为二进制值-仅0和1。如果分类特性中没有很多唯一的值,我更喜欢使用独热编码而不是标签编码。在这里,我在Region上使用了pandas的一个编码函数(get_dummies),并将其分成4列——location_NE、location_SE、location_NW和location_SW。也可以在本专栏中使用标签编码,但是,独热编码给了我更好的结果。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 #One hot encoding
 region=pd.get_dummies(df.region, prefix='location')
 df = pd.concat([df,region],axis=1)
 df.drop(columns='region', inplace=True)df.sex.replace(to_replace=['male','female'],value=[1,0], inplace=True)
 df.smoker.replace(to_replace=['yes', 'no'], value=[1,0], inplace=True)

特征选择和缩放

接下来,我们将选择最能影响“收费”的功能。我选择了除“性别”以外的所有功能,因为它对收费的影响很小(从上面的图表得出结论)。这些特征将构成变量X,而费用将构成变量y。如果有很多特性,我建议您使用scikit-learn的SelectKBest进行特性选择,以到达顶级特性。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 #Feature Selection 
 y=df.charges.values
 X=df[['age', 'bmi', 'smoker', 'children', 'location_northeast', 'location_northwest', 'location_southeast', 'location_southwest']]#Split data into test and train
 X_train, X_test, y_train, y_test=train_test_split(X,y, test_size=0.2, random_state=42)

一旦我们选择了我们的特征,我们需要“标准化”数字——年龄、BMI、儿童。标准化过程将数据转换为0到1范围内的更小的值,这样所有的值都处于相同的尺度上,而不是一个压倒另一个。我在这里使用了StandardScaler。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 #Scaling numeric features using sklearn StandardScalar
 numeric=['age', 'bmi', 'children']
 sc=StandardScalar()
 X_train[numeric]=sc.fit_transform(X_train[numeric])
 X_test[numeric]=sc.transform(X_test[numeric])

现在,我们已经准备好创建我们的第一个基本模型?。我们将尝试线性回归和决策树来预测保险费用

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 from sklearn.linear_model import LinearRegression
 from sklearn.tree import DecisionTreeRegressor
 from sklearn.metrics import r2_score, mean_absolute_error, mean_squared_error
 
 #Create a LinearRegression object
 lr= LinearRegression()
 #Fit X and y 
 lr.fit(X_train, y_train)
 ypred = lr.predict(X_test)
 #Metrics to evaluate your model 
 r2_score(y_test, ypred), mean_absolute_error(y_test, ypred), np.sqrt(mean_squared_error(y_test, ypred))
 
 
 dt = DecisionTreeRegressor()
 dt.fit(X_train, y_train)
 yhat = dt.predict(X_test)
 r2_score(y_test, yhat), mean_absolute_error(y_test, yhat), np.sqrt(mean_squared_error(y_test, yhat))

平均绝对误差(MAE)和均方根误差(RMSE)是用来评价回归模型的指标。你可以在这里阅读更多。我们的基线模型给出了超过76%的分数。在这两种方法之间,decision - trees给出的MAE更好为2780。

让我们看看如何使我们的模型更好。

特性工程

我们可以通过操纵数据集中的一些特征来提高模型得分。经过几次试验,我发现下面的项目可以提高准确性:

使用KMeans将类似的客户分组到集群中。

在区域栏中,将东北、西北区域划分为“北”区域,将东南、西南区域划分为“南”区域。

将' children '转换为一个名为' more_than_one_child '的分类特性,如果child的数量为> 1,则该特性为' Yes '

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 from sklearn.cluster import KMeans
 features=['age', 'bmi', 'smoker', 'children', 'location_northeast', 'location_northwest', 'location_southeast', 'location_southwest']
 kmeans = KMeans(n_clusters=2)
 kmeans.fit(df[features])
 
 df['cust_type'] = kmeans.predict(df[features])
 
 df['location_north']=df.apply(lambda x: get_north(x['location_northeast'], x['location_northwest']), axis=1
 
 df['location_south']=df.apply(lambda x: get_south(x['location_southwest'], x['location_southeast']), axis=1)
 
 df['more_than_1_child']=df.children.apply(lambda x:1 if x>1 else 0)

特征转换

从我们的EDA,我们知道“费用”(Y)的分布是高度倾斜的,因此我们将应用scikit-learn的目标转换- QuantileTransformer来标准化这种行为。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 X=df[['age', 'bmi', 'smoker', 'more_than_1_child', 'cust_type', 'location_north', 'location_south']]
 
 #Split test and train data
 X_train, X_test, y_train, y_test=train_test_split(X,y, test_size=0.2, random_state=42)
 
 model = DecisionTreeRegressor()
 regr_trans = TransformedTargetRegressor(regressor=model, transformer=QuantileTransformer(output_distribution='normal'))
 regr_trans.fit(X_train, y_train)
 yhat = regr_trans.predict(X_test)
 round(r2_score(y_test, yhat), 3), round(mean_absolute_error(y_test, yhat), 2), round(np.sqrt(mean_squared_error(y_test, yhat)),2)
 
 >>0.843, 2189.28, 4931.96

哇,惊人的84%,MAE已经降到了2189!

使用集成和增强算法

现在我们将使用这些功能的集成基于随机森林,梯度增强,LightGBM,和XGBoost。如果你是一个初学者,没有意识到boosting 和bagging 的方法。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 X=df[['age', 'bmi', 'smoker', 'more_than_1_child', 'cust_type', 'location_north', 'location_south']]
 
 model = RandomForestRegressor()
 #transforming target variable through quantile transformer
 ttr = TransformedTargetRegressor(regressor=model, transformer=QuantileTransformer(output_distribution='normal'))
 ttr.fit(X_train, y_train)
 yhat = ttr.predict(X_test)
 
 r2_score(y_test, yhat), mean_absolute_error(y_test, yhat), np.sqrt(mean_squared_error(y_test, yhat))
 
 >>0.8802, 2078, 4312

是的!我们的随机森林模型表现很好- 2078的MAE?。现在,我们将尝试一些增强算法,如梯度增强,LightGBM,和XGBoost。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 from sklearn.ensemble import GradientBoostingRegressor
 import lightgbm
 import xgboost
 
 #generic function to fit model and return metrics for every algorithm
 def boost_models(x):
     #transforming target variable through quantile transformer
     regr_trans = TransformedTargetRegressor(regressor=x, transformer=QuantileTransformer(output_distribution='normal'))
     regr_trans.fit(X_train, y_train)
     yhat = regr_trans.predict(X_test)
     algoname= x.__class__.__name__
     return algoname, round(r2_score(y_test, yhat),3), round(mean_absolute_error(y_test, yhat),2), round(np.sqrt(mean_squared_error(y_test, yhat)),2)
 
 algo=[GradientBoostingRegressor(), lgbm.LGBMRegressor(), xg.XGBRFRegressor()]
 score=[]
 for a in algo:
     score.append(boost_models(a))
 
  #Collate all scores in a table
  pd.DataFrame(score, columns=['Model', 'Score', 'MAE', 'RMSE'])

Hyperparameter调优

让我们调整一些算法参数,如树深度、估计值、学习率等,并检查模型的准确性。手动尝试参数值的不同组合非常耗时。Scikit-learn的GridSearchCV自动执行此过程,并计算这些参数的优化值。我已经将GridSearch应用于上述3种算法。下面是XGBoost的一个:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 from sklearn.model_selection import GridSearchCV
 
 param_grid = {'n_estimators': [100, 80, 60, 55, 51, 45],  
               'max_depth': [7, 8],
               'reg_lambda' :[0.26, 0.25, 0.2]
              }
                 
 grid = GridSearchCV(xg.XGBRFRegressor(), param_grid, refit = True, verbose = 3, n_jobs=-1) #
 regr_trans = TransformedTargetRegressor(regressor=grid, transformer=QuantileTransformer(output_distribution='normal'))
 
 # fitting the model for grid search 
 grid_result=regr_trans.fit(X_train, y_train)
 best_params=grid_result.regressor_.best_params_
 print(best_params)
 
 #using best params to create and fit model
 best_model = xg.XGBRFRegressor(max_depth=best_params["max_depth"], n_estimators=best_params["n_estimators"], reg_lambda=best_params["reg_lambda"])
 regr_trans = TransformedTargetRegressor(regressor=best_model, transformer=QuantileTransformer(output_distribution='normal'))
 regr_trans.fit(X_train, y_train)
 yhat = regr_trans.predict(X_test)
 
 #evaluate metrics
 r2_score(y_test, yhat), mean_absolute_error(y_test, yhat), np.sqrt(mean_squared_error(y_test, yhat))

一旦我们得到了参数的最优值,我们将使用这些值再次运行所有3个模型。

这个看起来好多了!我们已经能够提高我们的准确性- XGBoost给出了88.6%的分数,相对较少的错误

分布和残差图证实了预测费用和实际费用之间有很好的重叠。然而,有一些预测值远远超出了x轴,这使得我们的均方根误差更高。我们可以通过增加数据点(即收集更多数据)来减少这种情况。

现在我们已经准备好将这个模型部署到生产环境中,并在未知数据上对其进行测试。

简而言之,提高我模型准确性的要点

  • 创建简单的新特征
  • 转换目标变量
  • 聚类公共数据点
  • 使用增强算法
  • Hyperparameter调优

你可以在这里找到我的笔记本。并不是所有的方法都适用于你的模型。挑选最适合你的方案:)

https://github.com/sacharya225/data-expts/tree/master/Health%20Insurance%20Cost%20Prediction

作者:Shwetha Acharya

本文地址:https://towardsdatascience.com/how-to-improve-the-accuracy-of-a-regression-model-3517accf8604

deephub翻译组

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2021-06-15,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 DeepHub IMBA 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
python单细胞数据的基因集打分
随便一个h5文件即可。我这里使用的是pbmc3k,scanpy推文最后生成的文件就是它。
用户11414625
2024/12/20
2410
python单细胞数据的基因集打分
gseapy-python版的富集分析
富集分析分为超几何分布检验(ORA)和基因集富集分析(GSEA)。R语言有clusterprofiler包可以做富集,python是用gseapy。这个包功能强大,既支持两种富集分析,还支持基因集gmt的直接获取。
用户11414625
2024/12/20
3410
gseapy-python版的富集分析
python版本的功能富集分析:GSEApy
今天是第一篇,我们生信技能树前面推出了一个python单细胞课程:《掌握Python,解锁单细胞数据的无限可能》。群里学员问的最多的一个问题就是: python版本的功能富集分析如何做?一起来看看 python包:GSEApy。
生信技能树
2025/01/23
2880
python版本的功能富集分析:GSEApy
玩转scanpy和seurat对细胞群基因集打分和可视化基因集富集情况
在进行单细胞数据挖掘过程中,为了探明细胞亚群基因集的富集情况,通常会对细胞亚群进行基因集打分。通过对细胞亚群进行基因集打分,再通过画图可视化展示,可以看清各个细胞亚群的基因集富集情况,下面我们使用示例数据集通过scanpy和seurat进行基因集打分演示。
生信技能树jimmy
2024/04/01
1.5K0
玩转scanpy和seurat对细胞群基因集打分和可视化基因集富集情况
AddModuleScore 对单细胞基因集打分及可视化
在此选择的pathway通路及基因集(基于文章给出的部分基因)是我自己选用,并没有特别的生物学意义,只是做一下可视化展示。
生信菜鸟团
2023/10/07
3.9K0
AddModuleScore 对单细胞基因集打分及可视化
单细胞Scanpy流程学习和整理(分析簇间差异基因/细胞注释/数据保存)
上一篇推文介绍了Scanpy流程中的10X数据读取/过滤/降维/聚类步骤,这次笔者将学习一下差异分析/细胞注释/数据保存。
凑齐六个字吧
2024/09/26
1.1K0
单细胞Scanpy流程学习和整理(分析簇间差异基因/细胞注释/数据保存)
单细胞Scanpy流程学习和整理(单样本10X数据读取/过滤/降维/聚类)
新手上路写的很繁琐,多多包涵,本次用的IDE是Visual studio code。
凑齐六个字吧
2024/09/25
1.4K0
单细胞Scanpy流程学习和整理(单样本10X数据读取/过滤/降维/聚类)
单细胞测序最好的教程(六):细胞类型注释
作者按 本教程将是本系列教程中最重要的一章,我们后续所有的单细胞分析,都要基于准确的细胞类型注释。本系列教程首发于“[单细胞最好的中文教程](single_cell_tutorial Readthedocs[1])”,未经授权许可,禁止转载。 全文字数|预计阅读时间: 4500|5min ——Starlitnightly
生信技能树jimmy
2023/08/31
4.2K0
单细胞测序最好的教程(六):细胞类型注释
”基因集打分“GSEA算法详解
前两天介绍了一个开发中的单细胞数据分析相关R包,内置了,4(热图,气泡图,upset图,堆叠条形图)+4(密度散点图,半小提琴,山峦图,密度热图)美图,见 8种方法可视化你的单细胞基因集打分 ,蛮多小伙伴留言想问一下到底什么是基因集打分,正好学徒投稿了她自己的理解,借花献佛分享给大家。
生信技能树
2021/10/21
4.6K0
”基因集打分“GSEA算法详解
单细胞分析的 Python 包 Scanpy(图文详解)
线粒体基因的转录本比单个转录物分子大,并且不太可能通过细胞膜逃逸。因此,检测出高比例的线粒体基因,表明细胞质量差(Islam et al. 2014; Ilicic et al. 2016)。
白墨石
2021/07/16
5.4K1
单细胞分析的 Python 包 Scanpy(图文详解)
如何下载MSigDB数据库糖代谢相关基因
使用关键词在微信搜索中查找:MSigDB数据库糖代谢相关基因。搜到一篇 2022 年 10 月发表在 Frontiers in Endocrinology 杂志上的文章:Identification of risk model based on glycolysis-related genes in the metastasis of osteosarcoma。这个文章中用的是糖酵解相关基因集:
生信技能树
2025/02/07
4920
如何下载MSigDB数据库糖代谢相关基因
ChIP-seq 分析:基因集富集(11)
转录因子或表观遗传标记可能作用于按共同生物学特征(共享生物学功能、RNAseq 实验中的共同调控等)分组的特定基因组。
数据科学工厂
2023/03/21
7320
ChIP-seq 分析:基因集富集(11)
Scanpy 分析 3k PBMCs:寻找 marker 基因
本系列讲解 使用Scanpy分析单细胞(scRNA-seq)数据教程[1],持续更新,欢迎关注,转发!
数据科学工厂
2025/06/09
810
Scanpy 分析 3k PBMCs:寻找 marker 基因
python单细胞学习笔记-day7
今天继续学习视频:python_day6剩余部分和python_day7视频 !一口气学完吧!
生信技能树
2025/03/17
1500
python单细胞学习笔记-day7
借鉴escape包的一些可视化GSVA或者ssGSEA结果矩阵的方法
与此同时,不少粉丝对GSVA或者ssGSEA分析方法提出了要求,变相催稿。其实GSVA或者ssGSEA是有成熟的工具,我暂时没有找到它们的卖点。不过,我注意到了一个GitHub包,ncborcherding/escape,它提出来了对GSVA或者ssGSEA的分析结果的可视化,值得推荐。所以我们先介绍一下,假如你拿到了GSVA或者ssGSEA结果,如何可视化,这个时候呢,跟拟时序分析,转录因子分析,细胞通讯分析是大同小异的。去年我们在《生信技能树》公众号带领大家一起学习过:SCENIC转录因子分析结果的解读 ,以及:细胞通讯分析结果的解读,大家可以去读一读。
生信技能树
2021/01/18
3.6K0
借鉴escape包的一些可视化GSVA或者ssGSEA结果矩阵的方法
irGSEA:基于秩次的单细胞基因集富集分析整合框架
许多Functional Class Scoring (FCS)方法,如GSEA, GSVA,PLAGE, addModuleScore, SCSE, Vision, VAM, gficf, pagoda2和Sargent,都会受数据集组成的影响,数据集组成的轻微变化将改变细胞的基因集富集分数。
生信技能树
2023/12/05
3.1K0
irGSEA:基于秩次的单细胞基因集富集分析整合框架
scRNA分析|使用AddModuleScore 和 AUcell进行基因集打分,可视化
有了基因集文件除了做scRNA分析|单细胞GSVA + limma差异分析-celltype分组?样本分组?GSVA分析,还可以计算每个细胞的目标基因集评分 。
生信补给站
2023/08/25
18.7K0
scRNA分析|使用AddModuleScore 和 AUcell进行基因集打分,可视化
Science杂志高颜值GSEA打分排序图
关于可不可以用差异基因进行GSEA分析,我们前面讨论过:IF10+杂志文章只用统计学显著的差异基因做GSEA就合理吗?
生信技能树
2025/02/06
2650
Science杂志高颜值GSEA打分排序图
单细胞基因集打分方法——AUCell
「对于可视化部分,小提琴图,tSNE图或者umap图都可以展示出来AUCell打分得出的值。」
生信菜鸟团
2023/10/16
2.5K0
单细胞基因集打分方法——AUCell
python单细胞学习笔记-day6
https://cf.10xgenomics.com/samples/cell/pbmc3k/pbmc3k_filtered_gene_bc_matrices.tar.gz
生信技能树
2025/02/05
1440
python单细胞学习笔记-day6
推荐阅读
相关推荐
python单细胞数据的基因集打分
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档