**项目简介:**比赛由 Kaggle 举办,要求选手依据客户的信用卡信息,分期付款信息,信用局信息等预测客户贷款是否会违约。一共有8个数据集,包括1个主训练集,1个测试集和6个辅助信息表,主训练集特征主要有用户的个人属性,包括用户的性别,职业,是否有车,是否有房,房子面积等基本信息,辅助信息表包括用户的历史申请信息,历史账户余额信息,分期付款信息,信用卡信息,信用局信息和在信用局上的额度信息。
主训练集探索:
目的:
1、了解数据的缺失值情况、异常值情况,以便做对应的数据清洗
2、了解一下违约贷款和正常贷款用户画像的区别,加深对业务的理解,为我们后面的数据分析展开打基础
1、缺失值探索
# 读取训练集和测试集数据
app_train=pd.read_csv('./application_train.csv')
app_test = pd.read_csv('./application_test.csv')
#定义缺失值检测函数
def missing_values_table(df):
mis_val = df.isnull().sum() #对缺失值进行统计
mis_val_percent = 100 * df.isnull().sum() / len(df) #缺失值占比
mis_val_table = pd.concat([mis_val, mis_val_percent], axis=1) #
mis_val_table_ren_columns = mis_val_table.rename(
columns = {
0 : 'Missing Values', 1 : '% of Total Values'})# rename
mis_val_table_ren_columns =mis_val_table_ren_columns[mis_val_table_ren_columns.iloc[:,1] != 0].sort_values('% of Total Values', ascending=False).round(1) #对缺失值占比进行排序
return mis_val_table_ren_columns #返回缺失值列表
missing_values_table(app_train)
数据一共有122列,有67列存在缺失情况,最高缺失值的列缺失度为69.9%,可以发现前面的几列特征缺失度的都是一样的,并且它们都是属于房屋信息,根据这个规律我们可以猜测用户缺失房屋信息可能是因为某种特定原因导致的,而不是随机缺失,这点我们会在后面的特征工程用上。
2、异常值探索
查看用户年龄的数据分布情况(因为数据中,年龄的数值是负数,反映的是申请贷款前,这个用户活了多少天,所以这里我除了负365做了下处理),发现数据的分布还是比较正常的,最大年龄69岁,最小年龄20岁,没有很异常的数字
查看用户的工作时间分布情况发现(同样工作时间也是负数,所以我除了负365),最小值是-1000年,这里的-1000年明显是一个异常数据,没有人的工作时间是负数的,这可能是个异常值
看一下用户受工作时间的数据分布情况,发现所有的异常值都是一个值,365243,对于这个异常值我的理解是它可能是代表缺失值,所以我的选择是将这个异常值用空值去替换,这样可以保留这个信息,又抹去了异常值,替换之后我们再看一下工作时间的分布情况,正常了很多
3、违约用户画像探索
这部分分析的目标主要是查看违约用户和非违约用户的特征分布情况,目标是对违约用户的画像建立一个基本的了解,为后续特征工程打下基础。比如数据集里面有很多字段,包括性别、年龄、工作时间等等,那么是男性更容易违约还是女性?是年龄大的人更容易违约还是年龄小的人?查看这些数据,可以帮助我们对数据有更好的理解。
# 绘图函数,通过图形可以直观地看到数据的分布情况
def plot_stats(feature,label_rotation=False,horizontal_layout=True):
temp = app_train[feature].value_counts()
df1 = pd.DataFrame({
feature: temp.index,'Number of contracts': temp.values})
# Calculate the percentage of target=1 per category value
cat_perc = app_train[[feature, 'TARGET']].groupby([feature],as_index=False).mean()
cat_perc.sort_values(by='TARGET', ascending=False, inplace=True)
if(horizontal_layout):
fig, (ax1, ax2) = plt.subplots(ncols=2, figsize=(12,6))
else:
fig, (ax1, ax2) = plt.subplots(nrows=2, figsize=(12,14))
sns.set_color_codes("pastel")
s = sns.barplot(ax=ax1, x = feature, y="Number of contracts",data=df1)
if(label_rotation):
s.set_xticklabels(s.get_xticklabels(),rotation=90)
s = sns.barplot(ax=ax2, x = feature, y='TARGET', order=cat_perc[feature], data=cat_perc)
if(label_rotation):
s.set_xticklabels(s.get_xticklabels(),rotation=90)
plt.ylabel('Percent of target with value 1 [%]', fontsize=10)
plt.tick_params(axis='both', which='major', labelsize=10)
plt