这个比赛来自于这里
https://kesci.com/apps/home_log/index.html#!/competition/56cd5f02b89b5bd026cb39c9/content/0
1、数据清洗
加载数据的方法:
data = pd.read_csv(filename,encoding="gb1830")
原始数据中会有噪声,如果不做任何处理直接应用,回拉偏模型。
对缺失值的多维度处理
对于征信系统来说,用户提供的信息越完整,用户可信度越高,所以我们会很看重数据中的缺失值。
对于其它的场景可以具体处理。、
首先,观察数据缺失值的情况,包括横向和纵向两个方向观察。
panda中的方法
datafram.isnull().sum(axis=1) 每一行记录有几个缺失字段
datafrme.isnull().sum() 从列的维度进行观察,每一列有多少个记录是缺失值
对于缺失值比例非常高的列,其实可以直接删除。
对于缺失比例不高的列,而且如果是类别型的列,可以直接把缺失当作一个类别填充进来,比如用-1填充。
df['colname'].fillna(-1)
如果是数值型的列,我们可以用中位数等方法填充。
按行统计每个样本缺失属性的个数,然后按照缺失数量进行排序。并给每个样本一个序号。然后以序号作为横坐标,以缺失值个数作为纵坐标画出一个散点图。
对于训练数据和测试数据都是这样操作,于是画出两个散点图。
尽量保证训练数据和测试数据上缺失值的分布模式是一样的
观察这两个散点图的形状,有助于比较测试数据和训练数据的缺失值的模式是否一样。
对于其中明显不一样的部分,也就是说在训练数据中没有能够反应这些测试样本的测试集,所以训练出来的模型也可能不能很好的应用到这部分测试数据上。这部分训练数据可以作为离群点数据剔除。
对于变化幅度不大的列可以剔除
对于数值型特征,通过计算列的方差,来看属性值的波动情况。对于哪些非常小的列,可以剔除。
datafram.var()
对离群点的剔除方法
继续寻找离群点,由于离群点的异常特征可能来自于多个维度的组合,我们除了根据样本中缺失属性的个数剔除掉一些离群点。还可以这个做。
用xgboost得到特征的重要度,取前面最重要的n个特征,然后重点观察样本在这些特征上的缺失值个数,如果大于一定数量比如一半,也把这些样本作为离群点剔除。这也是一个合理的假设,既然这些特征最重要,但是你的记录却在这些特征上缺少关键数据,当然做出来的模型会不可靠。
这个地方可以画一个条形图来可视化。
get_fscore
文本处理
比如大小写统一变成小写,去掉多余的空格。尽量让相同含义的文本统一,不如省份统一都不带省字样。
dataframe['colname'].unique() 查看列上的值
2、特征工程
地理信息处理
在原始数据中,记录了用户的省市信息。属于类别型变量,对这种变量最常用的做法就是One-hot encoding。但是这样以来会得到很高维的稀疏特征。尤其是GBDT这种tree base的模型,这么多稀疏特征会让运行性能非常慢。
于是,作者在one-hot 基础上加上了特征选择。
从统计的角度做特征(处理省份信息)
这种方法是对那些取值比较少的类别型变量,肉眼可以观察的过来的,比如对省份直辖市,最多也不过就32个。
具体的做法是分层统计数据分布,其实就是看看哪些省市的违约率特别高,对于这些特别高的省份,我们单独提出来作为一个属性。
比如统计出四川、湖北、北京特别高。
于是可以构建三个二值特征,是否四川用户、是否湖北用户、是否北京用户。这样就用了三个one-hot变量取代了原来n多的one-hot变量。
借助xgboost筛选(处理城市信息)
对于地级市这样的特征,可能会有成百上千中看可能取值,这时再用基于统计的方法就观察不过来了。
这时我们就采用one-hot + xgboost的方法。
比如地级市这一列,one-hot之后得到400个二值属性。我们就在这400个二值属性上是用xgboost,然后得到特征的重要性。然后去最重要的城市做二值变量。
这一步其实就相当于数据降维
添加城市等级
比如一线城市是1,二线城市是2,三线城市是3。
添加经纬度
光有省市信息并不能体现更多的信息。现在我们引入经纬度,考虑地理上较劲的城市,违约率可能差不多,所以引入这部分信息。最终结果有千分之几的提升。
城市特征向量化
比如,对于数据集中的记录按照城市计数,然后做个等值离散化。
也就是某个城市落在什么样的人口区间,只不过是用样本中的记录数来作为人口属性。
更多的思考
比如,数据中有两个城市列,可能一个是出生城市,一个是工作城市。我们可以看看这两个城市是否一样,并作为一个特征加进来。
总之,如何引入更多的特征,取决于对于数据业务的理解。
成交时间处理
类别型编码
特征组合
gbdt做特征组合是有两种方式
其一:就是得到树的所有叶子节点结果
其二:根据特征重要度,这里用的方法
在这个案例中,作者用xgboost得到原始记录中特征的重要性,然后对于其中topn 重要的特征两两组合得到更多(7000+)特征,然后对这7000个组合特征单独训练模型。训练后又可以得到组合特征的重要程度。然后从中提取top500个组合特征,把这些组合特征加回到原始的特征中。
在这个案例中,作者选择待组合的特征都是数值型的,于是作者分别用了 两两相除的运算,然后取出top500,然后再做两两相乘取对数,又取出top200,把这700个都加回到原始特征体系中。
当然,并不一定必须加回到原始特征体系,也可以就使用组合特征去做模型。
3、特征选择
特征选择至少可以有三种方法:
根据一些指标,比如Person相关系数(衡量变量之间的线性相关性)
正则化方法(L1)
基于模型的特征重要性排序(xgboost),这里用的就是这个方法
用Xgboost的重要度排序
其实特征选择和特征工程是交叉在一起进行的。
4、类别不平衡的处理
也是有三种方式:
代价敏感学习
上采样(oversampling)
把多的类别拆成n份,每一份和少的一类做一个模型出来,最后n个模型投票。有点类似bagging。
代价敏感学习
修改损失函数
上采样
5、模型融合
参考Blending。
作者用了一个LR、一个gbdt、SVC
保证模型结果稳定
只是为了gbdt的稳定,作者通过对参数加入微小扰动生成30个gbdt,然后用折30个gbdt的输出的平均值作为整个gbdt的平均值,这么做只是希望gbdt模型的输出更稳定,这个思想可以用于所有算法
然后把这三个模型用blend方法做融合。