Kaggle竞赛——房价预测

目录

  • 1. 特征分析
    • 1.1 数据集导入
    • 1.2 统计缺失值
    • 1.3 可视化缺失值
    • 1.4 缺失值相关性分析
    • 1.5 训练集和测试集缺失数据对比
    • 1.6 统计特征的数据类型
    • 1.7 数值型特征分布直方图
    • 1.8 数值型特征与房价的线性关系
    • 1.9 非数值型特征的分布直方图
    • 1.10 非数值型特征箱线图
    • 1.11 数值型特征填充前后的分布对比
    • 1.12 时序特征分析
    • 1.13 用热图分析数值型特征之间的相关性
  • 2. 数据处理
    • 2.1 正态化 SalePrice
    • 2.2 时序特征处理
    • 2.3 特征融合
    • 2.4 填充特征值
    • 2.5 连续性数据正态化
    • 2.5 编码数据集后切分数据集
  • 3. 模型搭建
    • 3.1 模型搭建与超参数调整
    • 3.2 模型交叉验证
    • 3.3 特征重要性分析
    • 3.4 数值预测
  • 4. 参考文献

这是接触Kaggle竞赛的第一个题目,借鉴了其他人可视化分析和特征分析的技巧(文末附链接)。本次提交到Kaggle的得分是0.13227,排名1209(提交日期:2024年6月30日)。
在这里插入图片描述
思路简图:
在这里插入图片描述

1. 特征分析

1.1 数据集导入

将训练集与测试集合并,方便更准确地分析数据特征。

train = pd.read_csv("D:\\Desktop\\kaggle数据集\\house-prices-advanced-regression-techniques\\train.csv")
test  = pd.read_csv("D:\\Desktop\\kaggle数据集\\house-prices-advanced-regression-techniques\\test.csv")
Id = test['Id']
print("训练集大小{}".format(train.shape))
print("测试集大小{}".format(test.shape))
# 合并训练集与测试集,方便更准确地分析数据特征
datas = pd.concat([train, test], ignore_index=True)
# 删除Id列
datas.drop("Id", axis= 1, inplace=True)
训练集大小(1460, 81)
测试集大小(1459, 80)

1.2 统计缺失值

#------------------------------------------------------------------------------------------------------------#
# 统计数据集中的值的空缺情况(以列为统计单位)
# isnull():检查所有数据集,如果是缺失值则返回True,否则返回False
# .sum():计算每列中True的数量
#------------------------------------------------------------------------------------------------------------#
datas.isnull().sum().sort_values(ascending = False).head(40)
PoolQC           2909
MiscFeature      2814
Alley            2721
Fence            2348
MasVnrType       1766
SalePrice        1459
FireplaceQu      1420
LotFrontage       486
GarageFinish      159
GarageQual        159
GarageCond        159
GarageYrBlt       159
GarageType        157
BsmtCond           82
BsmtExposure       82
BsmtQual           81
BsmtFinType2       80
BsmtFinType1       79
MasVnrArea         23
MSZoning            4
BsmtHalfBath        2
Utilities           2
BsmtFullBath        2
Functional          2
Exterior2nd         1
Exterior1st         1
GarageArea          1
GarageCars          1
SaleType            1
KitchenQual         1
BsmtFinSF1          1
Electrical          1
BsmtFinSF2          1
BsmtUnfSF           1
TotalBsmtSF         1
TotRmsAbvGrd        0
Fireplaces          0
SaleCondition       0
PavedDrive          0
MoSold              0
dtype: int64

1.3 可视化缺失值

右侧的微线图概括了数据完整性的一般形状,并标明了具有最多空值(最靠近左侧,数值表示的该行中非空值的数量)和最少空值(最靠近右侧)的行。

msno.matrix(datas)

1.4 缺失值相关性分析

用热图显示数据集中缺失值之间的相关性

  • 1:表示两个特征的缺失模式完全相同,即其中一个缺失时,另一个也缺失
  • -1:表示一个特征有缺失值时,另一个特征没有缺失值
  • 0: 表示两个特征的缺失值模式不相关
msno.heatmap(train)

在这里插入图片描述

1.5 训练集和测试集缺失数据对比

#------------------------------------------------------------------------------------------------------------#
# 比较两个dataframe(train和test)的数据类型,需确保两个数据集具有相同的列标签
#------------------------------------------------------------------------------------------------------------#
train_dtype = train_dtype.drop('SalePrice')
train_dtype.compare(test_dtype)

在这里插入图片描述
由对比结果可知数据类型都是int64和float64的区别,对结果影响不大。

# 缺失值对比
null_train = train.isnull().sum()
null_test = test.isnull().sum()
null_train = null_train.drop('SalePrice')
null_comp = null_train.compare(null_test).sort_values(['self'], ascending=[False])
null_comp

(局部,未截完整)
在这里插入图片描述

1.6 统计特征的数据类型

  • 数值型特征
    • 1.1 离散特征(唯一值(多个重复值只取一个)数量小于25(可视情况而定))
    • 1.2 连续特征(‘Id’列不计入)
  • 非数值型数据
# 在 pandas 中,如果一个列的数据类型无法确定为数值型,则会被标记为 '0'
numerical_features = [col for col in datas.columns if datas[col].dtypes != 'O']
discrete_features = [col for col in numerical_features if len(datas[col].unique()) < 25]
continuous_features = [feature for feature in numerical_features if feature not in discrete_features]
non_numerical_features = [col for col in datas.columns if datas[col].dtype == 'O']print("Total Number of Numerical Columns : ",len(numerical_features))
print("Number of discrete features : ",len(discrete_features))
print("No of continuous features are : ", len(continuous_features))
print("Number of non-numeric features : ",len(non_numerical_features))print("离散型数据: ",discrete_features)
print("连续型数据:", continuous_features)
print("非数值型数据:",non_numerical_features)
Total Number of Numerical Columns :  37
Number of discrete features :  15
No of continuous features are :  22
Number of non-numeric features :  43
离散型数据:  ['MSSubClass', 'OverallQual', 'OverallCond', 'BsmtFullBath', 'BsmtHalfBath', 'FullBath', 'HalfBath', 'BedroomAbvGr', 'KitchenAbvGr', 'TotRmsAbvGrd', 'Fireplaces', 'GarageCars', 'PoolArea', 'MoSold', 'YrSold']
连续型数据: ['LotFrontage', 'LotArea', 'YearBuilt', 'YearRemodAdd', 'MasVnrArea', 'BsmtFinSF1', 'BsmtFinSF2', 'BsmtUnfSF', 'TotalBsmtSF', '1stFlrSF', '2ndFlrSF', 'LowQualFinSF', 'GrLivArea', 'GarageYrBlt', 'GarageArea', 'WoodDeckSF', 'OpenPorchSF', 'EnclosedPorch', '3SsnPorch', 'ScreenPorch', 'MiscVal', 'SalePrice']
非数值型数据: ['MSZoning', 'Street', 'Alley', 'LotShape', 'LandContour', 'Utilities', 'LotConfig', 'LandSlope', 'Neighborhood', 'Condition1', 'Condition2', 'BldgType', 'HouseStyle', 'RoofStyle', 'RoofMatl', 'Exterior1st', 'Exterior2nd', 'MasVnrType', 'ExterQual', 'ExterCond', 'Foundation', 'BsmtQual', 'BsmtCond', 'BsmtExposure', 'BsmtFinType1', 'BsmtFinType2', 'Heating', 'HeatingQC', 'CentralAir', 'Electrical', 'KitchenQual', 'Functional', 'FireplaceQu', 'GarageType', 'GarageFinish', 'GarageQual', 'GarageCond', 'PavedDrive', 'PoolQC', 'Fence', 'MiscFeature', 'SaleType', 'SaleCondition']

1.7 数值型特征分布直方图

离散数据分布直方图

#------------------------------------------------------------------------------------------------------------#
# 添加 Label 列用于标识训练集和测试集
#------------------------------------------------------------------------------------------------------------#
datas['Label'] = "Test"
datas['Label'][:1460] = "Train"
#------------------------------------------------------------------------------------------------------------#
# 离散数据直方图
# sharex=False:子图的x轴不共享,每个子图可以独立设置自己的x轴属性
# hue='Label':根据 Label 列的值为直方图上色,不同的 Label 值会分配不同颜色
# ax=axes[i%3,i//3]:确保了直方图可以在一个3xN的网格中均匀分布
#------------------------------------------------------------------------------------------------------------#
fig, axes = plt.subplots(3, 5, figsize=(30, 10), sharex=False)
for i, feature in enumerate(discrete_features):sns.histplot(data=datas, x=feature, hue='Label', ax=axes[i%3, i//3])

连续数据分布直方图

fig,axes = plt.subplots(nrows = 4, ncols = 6, figsize=(30,15), sharex=False)
for i, feature in enumerate(continuous_features):sns.histplot(data=datas, x=feature, hue='Label',ax=axes[i%4,i//4])

1.8 数值型特征与房价的线性关系

fig, axes = plt.subplots(7, 6, figsize=(30, 30), sharex=False)
for i, feature in enumerate(numerical_features):sns.scatterplot(data = datas, x = feature, y="SalePrice", ax=axes[i%7, i//7])

1.9 非数值型特征的分布直方图

f,axes = plt.subplots(7, 7, figsize=(30,30),sharex=False)
for i,feature in enumerate(non_numerical_features):sns.countplot(data=datas, x=feature, hue="Label", ax=axes[i%7,i//7])

1.10 非数值型特征箱线图

对每个箱线图内部按照 SalePric 对不同的特征值进行降序排序。

#------------------------------------------------------------------------------------------------------------#
# groupby(feature)['SalePrice'].median():计算每个 feature 分组的SalePrice中位数
# items():将结果转换为一个包含键值对的迭代器(迭代器中的每个元素都是一个二元组),二元组形式:(特征值,中位数)
# x[1]:根据二元组的第二个值进行排序
# reverse = True:降序
# x[0] for x in sort_list:提取二元组的第一个值(键)即特征值
# order=order_list:按 order_list 中的顺序排列 x 轴的分类
#------------------------------------------------------------------------------------------------------------#
fig, axes = plt.subplots(7,7 , figsize=(30, 30), sharex=False)
for i, feature in enumerate(non_numerical_features):sort_list = sorted(datas.groupby(feature)['SalePrice'].median().items(), key = lambda x:x[1], reverse = True)order_list = [x[0] for x in sort_list ]sns.boxplot(data = datas, x = feature, y = 'SalePrice', order=order_list, ax=axes[i%7, i//7])
plt.show()

在这里插入图片描述

1.11 数值型特征填充前后的分布对比

# 原数值数据数据(有数据缺失的列)与使用均值、众数和中位数填充后的数据分布对比
null_numerical_features = [col for col in datas.columns if datas[col].isnull().sum()>0 and col not in non_numerical_features]
plt.figure(figsize=(30, 20))for i, var in enumerate(null_numerical_features):plt.subplot(4,3,i+1)sns.distplot(datas[var], bins=20, kde_kws={'linewidth':3,'color':'yellow'}, label="original")sns.distplot(datas[var].fillna(datas[var].mean()), bins=20, kde_kws={'linewidth':2,'color':'red'}, label="mean")sns.distplot(datas[var].fillna(datas[var].median()), bins=20, kde_kws={'linewidth':2,'color':'green'}, label="median")sns.distplot(datas[var].fillna(datas[var].mode()[0]), bins=20, kde_kws={'linewidth':2,'color':'blue'}, label="mode") 

1.12 时序特征分析

#------------------------------------------------------------------------------------------------------------#
# YrSold是离散型数据,YearBuilt(建房日期),YearRemodAdd(改造日期),GarageYrBlt(车库修建日期)是连续型数据
#------------------------------------------------------------------------------------------------------------#
year_feature = [col for col in datas.columns if "Yr" in col or 'Year' in col]
year_feature
['YearBuilt', 'YearRemodAdd', 'GarageYrBlt', 'YrSold']
# 查看YrSold与售价的关系
datas.groupby('YrSold')['SalePrice'].median().plot()
plt.xlabel('Year Sold')
plt.ylabel('House Price')
plt.title('House price vs YearSold')

# 绘制其他三个特征与销售价格的散点对应图
for feature in year_feature:if feature != 'YrSold':hs = datas.copy()plt.scatter(hs[feature],hs['SalePrice'])plt.xlabel(feature)plt.ylabel('SalePrice')


可以发现随着时间增加(即建造的时间越近),价格也逐渐增加。

1.13 用热图分析数值型特征之间的相关性

#------------------------------------------------------------------------------------------------------------#
# cmap="YlGnBu":指定从黄绿色(正相关)到蓝绿色(负相关)的颜色渐变
# linewidths=.5:边框宽度为0.5
#------------------------------------------------------------------------------------------------------------#
plt.figure(figsize=(20,10))
numeric_features = train.select_dtypes(include=[float, int])
sns.heatmap(numeric_features.corr(), cmap="YlGnBu", linewidths=.5)

2. 数据处理

2.1 正态化 SalePrice

  • n p . l o g 1 ( ) np.log1() np.log1():即计算 l n ( 1 + x ) ln(1 + x) ln(1+x),使用该函数比直接使用 n p . l o g ( 1 + x ) np.log(1 + x) np.log(1+x) 计算的精度要高。注意:np.log() 函数指的是计算自然对数)
  • n p . e x p m 1 ( ) np.expm1() np.expm1():即计算 e x − 1 e^x-1 ex1,使用该函数比直接计算 e x − 1 e^x-1 ex1 的精度要高。

二者互为反函数,使用 n p . l o g 1 ( ) np.log1() np.log1() 将 SalePrice 平滑化(正态化)后,最后得到的预测值需要用 n p . e x p m 1 ( ) np.expm1() np.expm1() 进行转换。

#------------------------------------------------------------------------------------------------------------#
# 绘制SalePrice的特征分布
# displot:用于绘制直方图和核密度估计图
# kde:用于在直方图上叠加核密度估计曲线
# .skew():算数据集的偏度,偏度是统计数据分布的不对称性的度量
#------------------------------------------------------------------------------------------------------------#
sns.displot(datas['SalePrice'], color='g', bins=50, kde=True)
print("SalePrice的偏度:{:.2f}".format(datas['SalePrice'].skew()))
SalePrice的偏度:1.88

在这里插入图片描述

#------------------------------------------------------------------------------------------------------------#
# 使用 np.log1() 将其平滑化(正态化)
# 偏度为1.88,SalePrice 的数据分布显著偏离正态,正常的数据应该是接近于正态分布的
#------------------------------------------------------------------------------------------------------------#
datas['SalePrice'] = np.log1p(datas['SalePrice'])
sns.displot(datas['SalePrice'], color='g', bins=50, kde=True)
print("正态化后 SalePrice 的偏度:{:.2f}".format(datas['SalePrice'].skew()))
正态化后 SalePrice 的偏度:0.12

在这里插入图片描述

2.2 时序特征处理

将时序特征离散化(用 YrSold 减去 YearBuilt、YearRemodAdd和GarageYrBlt 的时间),YrSold本身离散不用管。时序特征中 GarageYrBlt 数据有缺失,用中位数补足。

for feature in ['YearBuilt','YearRemodAdd','GarageYrBlt']:datas[feature]=datas['YrSold']-datas[feature]
datas['GarageYrBlt'].fillna(datas['GarageYrBlt'].median(), inplace = True)

2.3 特征融合

从非数值型特征的分布直方图中可以发现 GarageQual 特征的 Ex 和 Po 占比非常小(如下图),所以将这两个特征值统称为 other(其他列暂不使用,还不知道效果如何)。
在这里插入图片描述

# mask是一个布尔索引数组,长度与列 cGarageQual 的长度相同
# datas['GarageQual'][mask]:选择列 GarageQual 中所有 mask 为 True 的元素,
mask = datas['GarageQual'].isin(['Ex', 'Po'])
datas['GarageQual'][mask] = 'Other'

2.4 填充特征值

缺失最多的特征 PoolQC(泳池质量)并不代表数据缺失,而是没有泳池,因此不能简单地直接删除该列,这里用None替换掉Nan。

datas['PoolQC'].fillna("None", inplace=True)

排查数据缺失列,如果是数值型特征则根据数据 [1.11 数值型特征填充前后的分布对比] 选择中位数、众数还是平均数填充(多数情况下离散型用众数或中位数,连续型用中位数或平均数)。
如果是非数值型数据分两种情况:

  1. 缺失较多,使用 None 填充(新加一个类)
  2. 缺失较少,使用众数(最大类别)填充
# -------------------------------------------------非数值型数据----------------------------------------------#
datas['MiscFeature'].fillna('None', inplace=True)
datas['Alley'].fillna('None', inplace=True)
datas['Fence'].fillna('None', inplace=True)
datas['MasVnrType'].fillna('None', inplace=True)
datas['FireplaceQu'].fillna('None', inplace=True)
datas['GarageQual'].fillna('None', inplace=True)
datas['GarageCond'].fillna('None', inplace=True)
datas['GarageFinish'].fillna('None', inplace=True)
datas['GarageType'].fillna('None', inplace=True)
datas['BsmtCond'].fillna('None', inplace=True)
datas['BsmtExposure'].fillna('None', inplace=True)
datas['BsmtQual'].fillna('None', inplace=True)
datas['BsmtFinType1'].fillna('None', inplace=True)
datas['BsmtFinType2'].fillna('None', inplace=True)# mode()[0]:计算该列的众数并取第一个值
datas['MSZoning'].fillna(datas['MSZoning'].mode()[0], inplace=True)
datas['Utilities'].fillna(datas['Utilities'].mode()[0], inplace=True)
datas['Functional'].fillna(datas['Functional'].mode()[0], inplace=True)
datas['Electrical'].fillna(datas['Electrical'].mode()[0], inplace=True)
datas['Exterior2nd'].fillna(datas['Exterior2nd'].mode()[0], inplace=True)
datas['Exterior1st'].fillna(datas['Exterior1st'].mode()[0], inplace=True)
datas['SaleType'].fillna(datas['SaleType'].mode()[0], inplace=True)
datas['KitchenQual'].fillna(datas['KitchenQual'].mode()[0], inplace=True)#--------------------------------------------------数值型数据------------------------------------------------#
datas['MasVnrArea'].fillna(datas['MasVnrArea'].mean(), inplace = True)
datas['LotFrontage'].fillna(datas['LotFrontage'].mean(), inplace = True)
datas['BsmtFullBath'].fillna(datas['BsmtFullBath'].median(), inplace = True)
datas['BsmtHalfBath'].fillna(datas['BsmtHalfBath'].median(), inplace = True)
datas['BsmtFinSF1'].fillna(datas['BsmtFinSF1'].median(), inplace = True)
datas['GarageCars'].fillna(datas['GarageCars'].mean(), inplace = True)
datas['GarageArea'].fillna(datas['GarageArea'].mean(), inplace = True)
datas['TotalBsmtSF'].fillna(datas['TotalBsmtSF'].mean(), inplace = True)
datas['BsmtUnfSF'].fillna(datas['BsmtUnfSF'].mean(), inplace = True)
datas['BsmtFinSF2'].fillna(datas['BsmtFinSF2'].median(), inplace = True)

数据填充完之后确认一下是否还有遗漏的数据

datas.isnull().sum().sort_values(ascending = False).head(10)
SalePrice       1459
MSZoning           0
GarageYrBlt        0
GarageType         0
FireplaceQu        0
Fireplaces         0
Functional         0
TotRmsAbvGrd       0
KitchenQual        0
KitchenAbvGr       0
dtype: int64

2.5 连续性数据正态化

数据填充完毕后,重新挑选出连续型数值特征,观察其分布情况。

numerical_features = [col for col in datas.columns if datas[col].dtypes != 'O']
discrete_features = [col for col in numerical_features if len(datas[col].unique()) < 25 and col not in ['Id']]
continuous_features = [feature for feature in numerical_features if feature not in discrete_features+['Id']]
fig,axes = plt.subplots(nrows = 4, ncols = 6, figsize=(30,15), sharex=False)
for i, feature in enumerate(continuous_features):sns.histplot(data=datas, x=feature, hue='Label',ax=axes[i%4,i//4])

在这里插入图片描述
通过直方图可以直观地看出数值的分布是否符合正态分布,再分别计算偏度,通过偏度查看数据的偏离情况。

# 计算偏度
skewed_features = datas[continuous_features].apply(lambda x:x.skew()).sort_values(ascending=False)
print(skewed_features)
MiscVal          21.958480
LotArea          12.829025
LowQualFinSF     12.094977
3SsnPorch        11.381914
BsmtFinSF2        4.148275
EnclosedPorch     4.005950
ScreenPorch       3.948723
MasVnrArea        2.612892
OpenPorchSF       2.536417
WoodDeckSF        1.843380
LotFrontage       1.646420
1stFlrSF          1.470360
BsmtFinSF1        1.426111
GrLivArea         1.270010
TotalBsmtSF       1.163082
BsmtUnfSF         0.919981
2ndFlrSF          0.862118
YearBuilt         0.598917
YearRemodAdd      0.450458
GarageYrBlt       0.392261
GarageArea        0.241342
SalePrice         0.121347
dtype: float64

这里将偏度大于 1.5 的特征进行正态化,值设得太大的话正态化之后会导致原本0-1之间的特征的偏度过于小(-4左右)而出现左偏斜(即数据集中有较多较小的值)。

# 如果偏度的绝对值大于1.5,则用np.log1p进行处理【注:并不保证处理后偏度就会小于1.5,只能是使数据尽量符合正态分布】
# 需要正则化的特征列
log_list=[]
for feature, skew_value in skewed_features.items():if skew_value > 1.5:log_list.append(feature)
log_list# 正则化
for i in log_list:datas[i] = np.log1p(datas[i])# 检查正则化情况
skewed_features = datas[continuous_features].apply(lambda x:x.skew()).sort_values(ascending=False)
print(skewed_features)
3SsnPorch        8.829794
LowQualFinSF     8.562091
MiscVal          5.216665
ScreenPorch      2.947420
BsmtFinSF2       2.463749
EnclosedPorch    1.962089
1stFlrSF         1.470360
BsmtFinSF1       1.426111
GrLivArea        1.270010
TotalBsmtSF      1.163082
BsmtUnfSF        0.919981
2ndFlrSF         0.862118
YearBuilt        0.598917
MasVnrArea       0.504832
YearRemodAdd     0.450458
GarageYrBlt      0.392261
GarageArea       0.241342
WoodDeckSF       0.158114
SalePrice        0.121347
OpenPorchSF     -0.041819
LotArea         -0.505010
LotFrontage     -1.019985
dtype: float64

由结果可知,3SsnPorch、LowQualFinSF 和 MiscVal 的偏度还是太大(正偏度值大于2通常被认为是严重的右偏斜),但此时不宜再对这三个特征再次进行正态化,否则可能会导致数据失真。

2.5 编码数据集后切分数据集

# 删除Label列后对数据集进行独热(One-hot)编码
datas.drop('Label', axis=1, inplace=True)
datas = pd.get_dummies(datas, dtype=int)
# 切分训练集和测试集
new_train= datas.iloc[:len(train), :]
new_test = datas.iloc[len(train):, :]
X_train = new_train.drop('SalePrice', axis=1)
Y_train = new_train['SalePrice']
X_test = new_test.drop('SalePrice', axis=1)

3. 模型搭建

3.1 模型搭建与超参数调整

import optuna
from sklearn.linear_model import Ridge
from xgboost import XGBRegressor
from sklearn.ensemble import GradientBoostingRegressor
from sklearn.model_selection import cross_val_score"""
定义超参数优化函数
Params:objective:待优化的评估函数
Returns:params:最佳超参数组合
"""
def tune(objective):# 创建了一个 Optuna 的 Study 对象,用于管理一次超参数优化的过程# direction='maximize' 表示优化的目标是最大化目标函数的返回值(返回值是负的均方根误差)study = optuna.create_study(direction='maximize')# 使用 study 对象的 optimize 方法来执行优化过程# n_trials=100:指定了进行优化的试验次数study.optimize(objective, n_trials=10)params = study.best_params# 获取经过优化后的最佳得分((目标函数的返回值))best_score = study.best_valueprint(f"Best score: {-best_score} \nOptimized parameters: {params}")return params"""
Ridge回归
Params:trial:是由 Optuna 库提供的对象,用于在超参数优化过程中管理参数的提议和跟踪
Returns:score:交叉验证评分
"""
def ridge_objective(trial):# 0.1 是超参数的下界,20 是超参数的上界。Optuna 会在指定的范围内为超参数 alpha 提出一个值_alpha = trial.suggest_float("alpha",0.1,20)ridge = Ridge(alpha=_alpha, random_state=1)score = cross_val_score(ridge,X_train,Y_train, cv=10, scoring="neg_root_mean_squared_error").mean()return score"""
梯度增强树回归
Params:trial:是由 Optuna 库提供的对象,用于在超参数优化过程中管理参数的提议和跟踪
Returns:score:交叉验证评分
"""
def gbr_objective(trial):_n_estimators = trial.suggest_int("n_estimators", 50, 2000)_learning_rate = trial.suggest_float("learning_rate", 0.01, 1)_max_depth = trial.suggest_int("max_depth", 1, 20)
#     _min_samp_split = trial.suggest_int("min_samples_split", 2, 20)
#     _min_samples_leaf = trial.suggest_int("min_samples_leaf", 2, 20)
#     _max_features = trial.suggest_int("max_features", 10, 50)gbr = GradientBoostingRegressor(n_estimators=_n_estimators,learning_rate=_learning_rate,max_depth=_max_depth, 
#         max_features=_max_features,
#         min_samples_leaf=_min_samples_leaf,
#         min_samples_split=_min_samp_split,random_state=1,)score = cross_val_score(gbr, X_train,Y_train, cv=10, scoring="neg_root_mean_squared_error").mean()return score"""
XGBoost回归模型
Params:trial:是由 Optuna 库提供的对象,用于在超参数优化过程中管理参数的提议和跟踪
Returns:score:交叉验证评分
"""
def xgb_objective(trial):_n_estimators = trial.suggest_int("n_estimators", 50, 2000)_max_depth = trial.suggest_int("max_depth", 1, 20)_learning_rate = trial.suggest_float("learning_rate", 0.01, 1)
#     _gamma = trial.suggest_float("gamma", 0.01, 1)
#     _min_child_weight = trial.suggest_float("min_child_weight", 0.1, 10)
#     _subsample = trial.suggest_float('subsample', 0.01, 1)
#     _reg_alpha = trial.suggest_float('reg_alpha', 0.01, 10)
#     _reg_lambda = trial.suggest_float('reg_lambda', 0.01, 10)xgboost = XGBRegressor(n_estimators=_n_estimators,max_depth=_max_depth, learning_rate=_learning_rate,
#         gamma=_gamma,
#         min_child_weight=_min_child_weight,
#         subsample=_subsample,
#         reg_alpha=_reg_alpha,
#         reg_lambda=_reg_lambda,
#         random_state=1,)score = cross_val_score(xgboost, X_train, Y_train, cv=10, scoring="neg_root_mean_squared_error").mean()return score

寻找最佳参数,运行下面代码很耗时,可适当减少不重要参数的调优。本地调优后官网提交时不用再次运行,直接用本地运行的最佳参数即可。

# 设置日志级别为 WARNING,减少输出信息的数量
# optuna.logging.set_verbosity(optuna.logging.WARNING)ridge_params = tune(ridge_objective)
# Best score: 0.13482720346041538 
# Optimized parameters: {'alpha': 14.933121817345844}
# ridge_params = {'alpha': 14.933121817345844}gbr_params = tune(gbr_objective)
# Best score: 0.1388996815131788 
# Optimized parameters: {'n_estimators': 928, 'learning_rate': 0.24282934638611978, 'max_depth': 7}
# gbr_params = {'n_estimators': 928, 'learning_rate': 0.24282934638611978, 'max_depth': 7}xbg_params = tune(xgb_objective)
# Best score: 0.12403838351336531 
# Optimized parameters: {'n_estimators': 1713, 'max_depth': 3, 'learning_rate': 0.030462678052628034}
# xbg_params = {'n_estimators': 1713, 'max_depth': 3, 'learning_rate': 0.030462678052628034}# **:用于将键值对作为关键字参数传递给函数
ridge = Ridge(**ridge_params, random_state=1)
gbr = GradientBoostingRegressor(**gbr_params, random_state=1)
xgboost = XGBRegressor(**xbg_params, random_state=1)

3.2 模型交叉验证

ridge_score = np.sqrt(-cross_val_score(ridge, X_train, Y_train, cv=10, scoring='neg_mean_squared_error')) 
gbr_score = np.sqrt(-cross_val_score(gbr, X_train, Y_train, cv=10, scoring='neg_mean_squared_error')) 
xgboost_score = np.sqrt(-cross_val_score(xgboost, X_train, Y_train, cv=10, scoring='neg_mean_squared_error')) 
print(f"ridge_score: {np.mean(ridge_score)}")
print(f"gbr_score: {np.mean(gbr_score)}")
print(f"xgboost_score: {np.mean(xgboost_score)}")
ridge_score: 0.13482720346041538
gbr_score: 0.1388996815131788
xgboost_score: 0.12403838351336531

3.3 特征重要性分析

xgboost.fit(X_train, Y_train)
# 删除 "SalePrice" 方便分析特征重要性
imp_datas = datas.drop("SalePrice", axis=1)# 获取特征重要性
importance = xgboost.feature_importances_# 创建特征名称与重要性映射,用于合并独热编码之后的特征
feature_importance = pd.Series(importance, index=imp_datas.columns)# 提取独热编码的特征名
original_feature_names = [col.split('_')[0] for col in imp_datas.columns]# 聚合特征重要性
aggregated_importance = feature_importance.groupby(original_feature_names).sum()plt.figure(figsize=(10, 18))# kind='barh':指定了绘图类型为水平条形图
# sort_values()本身是由小到大的排序,但使用 .plot(kind='barh') 时,水平条形图的 y 轴将显示由高到低的顺序
aggregated_importance.sort_values().plot(kind='barh')
plt.xlabel("Feature Importance")
plt.ylabel('Feature')
plt.title("Aggregated Feature Importance Ranking")
# 调整图表布局,使其更紧凑
plt.tight_layout()

在这里插入图片描述

3.4 数值预测

选择最佳模型xgboost预测售价。

xgboost.fit(X_train, Y_train)
predictions = np.expm1(xgboost.predict(X_test))
submission = pd.DataFrame({'Id': Id,'SalePrice': predictions})
# submission.to_csv('/kaggle/working/submission.csv', index=False)
print('Submission file created!')

4. 参考文献

[1] 机器学习/深度学习实战——kaggle房价预测比赛实战(数据分析篇)
[2] kaggle简单实战——房价预测(xgboost实现)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/38675.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

JAVA:常用的算法指南

请关注微信公众号&#xff1a;拾荒的小海螺 博客地址&#xff1a;http://lsk-ww.cn/ 1、简述 在软件开发过程中&#xff0c;算法扮演着关键的角色。它们用于解决各种问题&#xff0c;从数据处理到搜索、排序等。本文将介绍几种常见的算法及其 Java 实现&#xff0c;包括排序算…

基于java+springboot+vue实现的农产品直卖平台(文末源码+Lw)266

摘 要 计算机网络发展到现在已经好几十年了&#xff0c;在理论上面已经有了很丰富的基础&#xff0c;并且在现实生活中也到处都在使用&#xff0c;可以说&#xff0c;经过几十年的发展&#xff0c;互联网技术已经把地域信息的隔阂给消除了&#xff0c;让整个世界都可以即时通…

Python从0到100(三十三):xpath和lxml类库

1. 为什么要学习xpath和lxml lxml是一款高性能的 Python HTML/XML 解析器&#xff0c;我们可以利用XPath&#xff0c;来快速的定位特定元素以及获取节点信息 2. 什么是xpath XPath&#xff0c;全称为XML Path Language&#xff0c;是一种用于在XML文档中进行导航和数据提取的…

Python基础之多进程

文章目录 1 多进程1.1 简介1.2 Linux下多进程1.3 multiprocessing1.4 Pool1.5 进程间通信1.6 分布式进程 1 多进程 1.1 简介 要让Python程序实现多进程&#xff08;multiprocessing&#xff09;&#xff0c;我们先了解操作系统的相关知识。 Unix/Linux操作系统提供了一个fork…

豆包文科成绩超了一本线,为什么理科不行?

卡奥斯智能交互引擎是卡奥斯基于海尔近40年工业生产经验积累和卡奥斯7年工业互联网平台建设的最佳实践&#xff0c;基于大语言模型和RAG技术&#xff0c;集合海量工业领域生态资源方优质产品和知识服务&#xff0c;旨在通过智能搜索、连续交互&#xff0c;实时生成个性化的内容…

Java - 程序员面试笔记记录 实现 - Part2

2.1 输入输出流 流可以被看作一组有序的字节集合&#xff0c;即数据在两个设备间的传输。 字节流&#xff1a;以字节作为单位&#xff0c;读到一个字节就返回一个字节&#xff1b;InputStream & OutputStream。 字符流&#xff1a;使用字节流读到一个到多个字节先查询码…

基于RabbitMQ的异步消息传递:发送与消费

引言 RabbitMQ是一个流行的开源消息代理&#xff0c;用于在分布式系统中实现异步消息传递。它基于Erlang语言编写&#xff0c;具有高可用性和可伸缩性。在本文中&#xff0c;我们将探讨如何在Python中使用RabbitMQ进行消息发送和消费。 安装RabbitMQ 在 Ubuntu 上安装 Rabbi…

提升写作效率:探索AI在现代办公自动化中的应用

工欲善其事&#xff0c;必先利其器。 随着AI技术与各个行业或细分场景的深度融合&#xff0c;日常工作可使用的AI工具呈现出井喷式发展的趋势&#xff0c;AI工具的类别也从最初的AI文本生成、AI绘画工具&#xff0c;逐渐扩展到AI思维导图工具、AI流程图工具、AI生成PPT工具、AI…

ubuntu 系统中 使用docker 制作 Windows 系统,从此告别 vmware虚拟机

我的系统是 ubuntu 24 前期准备工作&#xff1a; 安装dockerdocker pull 或者 手动制作镜像 docker build 的话 必须要 科学上网&#xff0c; 好像阿里镜像都下不下来。需要 知道 docker 和docker compose 命令的使用方式 我是给docker 挂了 http代理 如果你能pull下来镜像 …

springboot健身房管理系统-计算机毕业设计源码031807

摘 要 大数据时代下&#xff0c;数据呈爆炸式地增长。为了迎合信息化时代的潮流和信息化安全的要求&#xff0c;利用互联网服务于其他行业&#xff0c;促进生产&#xff0c;已经是成为一种势不可挡的趋势。在健身房管理的要求下&#xff0c;开发一款整体式结构的健身房管理系统…

Windows环境使用SpringBoot整合Minio平替OSS

目录 配置Minio环境 一、下载minio.exe mc.exe 二、设置用户名和密码 用管理员模式打开cmd 三、启动Minio服务器 四、访问WebUI给的地址 SpringBoot整合Minio 一、配置依赖&#xff0c;application.yml 二、代码部分 FileVO MinioConfig MinioUploadService MinioController 三…

使用Python绘制太阳系图

使用Python绘制太阳系图 太阳系图太阳系图的优点使用场景 效果代码 太阳系图 太阳系图&#xff08;Sunburst Chart&#xff09;是一种层次结构图表&#xff0c;用于表示数据的分层结构。它使用同心圆表示各个层级&#xff0c;中心圆代表最高层级&#xff0c;向外的圆环代表逐级…

CCT技术

概念介绍 多个功能核心的集成可以通过片上系统(SOC)或封装中系统(SIP)设备的开发来实现。SOC器件将核心集成到单个集成电路中。SIP集成是将多个集成电路组合到单个封装中。核心数量 的增加可能导致必要的测试人员资源和/或测试时间的增加。这直接影响了与测试这些设备相关的…

CesiumJS【Basic】- #031 绘制虚线(Entity方式)

文章目录 绘制虚线(Entity方式)1 目标2 代码2.1 main.ts绘制虚线(Entity方式) 1 目标 使用Entity方式绘制虚线 2 代码 2.1 main.ts import * as Cesium from cesium;const viewer = new Cesium.Viewer(

SAP实现特别总账的凭证预制

SAP实现特别总账的凭证预制 仔细理解只有”其他”的特殊总帐标识才可预制凭证这句话. F-29/f-48不可预制。F-29/f-48预制时出现错误消息号 FP 030&#xff0c;提示特殊总帐标志类型“汇票和”预付定金“的特别总帐标志的过帐代码不能预制&#xff0c;这是系统写死的&#xff…

现在电气真的比不过计算机吗 ?

电气工程和计算机科学在今天的科技和工业领域中各有其重要性和发展空间&#xff0c;并不存在简单的比较谁“比不过”谁的情况。我收集制作一份plc学习包&#xff0c;对于新手而言简直不要太棒&#xff0c;里面包括了新手各个时期的学习方向&#xff0c;包括了编程教学&#xff…

Pycharm的终端(Terminal)中切换到当前项目所在的虚拟环境

1.在Pycharm最下端点击终端/Terminal, 2.点击终端窗口最上端最右边的∨&#xff0c; 3.点击Command Prompt&#xff0c;切换环境&#xff0c; 可以看到现在环境已经由默认的PS(Window PowerShell)切换为项目所使用的虚拟环境。 4.更近一步&#xff0c;如果想让Pycharm默认显示…

Linux常用工具使用方式

目录 常用工具&#xff1a; 安装包管理工具&#xff1a; 查找含有关键字的软件包 安装软件 安装文件传输工具 安装编辑器 C语言编译器 C编译器 安装调试器 安装项目版本管理工具 cmake 卸载软件 安装jsoncpp 安装boost库 安装mariadb 安装tree&#xff08;让目录…

潜水耳机哪个牌子好?用户精选,这四款潜水耳机质量上乘!

在这个快节奏的时代&#xff0c;人们越来越渴望在运动中也能享受到音乐的陪伴。潜水&#xff0c;作为一种独特的水下运动&#xff0c;自然也不例外。然而&#xff0c;并非所有的耳机都能承受水下的压力和环境&#xff0c;这就要求我们对潜水耳机有着更高的要求。作为一名资深的…

Kubernetes的发展历程:从Google内部项目到云原生计算的基石

目录 一、起源与背景 1.1 Google的内部项目 1.2 Omega的出现 二、Kubernetes的诞生 2.1 开源的决策 2.2 初期发布 三、Kubernetes的发展历程 3.1 社区的成长 3.2 生态系统的壮大 3.3 重大版本和功能 3.4 多云和混合云的支持 四、Kubernetes的核心概念 4.1 Pod 4.…