предисловие
当我们拿到一批原始数据
首先要明确有多少特征,哪些是连续特征,哪些是类别特征(离散特征)。
检查有没有缺失值,对有缺失值的特征选择恰当方式进行弥补,使数据完整(或者把该特征删除)
对连续型型特征进行标准化或者归一化,
对类别型特征进行one-hot编码(没有大小关系)或者序号编码(有大小关系)。
将需要转换成类别型数据的连续型数据进行二值化。
为防止过拟合或者其他原因,选择是否要将数据进行正则化。
在对数据进行初探之后发现效果不佳,可以尝试使用多项式方法,寻找非线性的关系。
根据实际问题分析是否需要对特征进行相应的函数转换。
是否需要进行特征组合,得到新的特征。
1/Стандартизация: удалить среднее, масштабировать дисперсию
Standardization标准化,
将特征数据的分布调整成标准正太分布,也叫高斯分布,也就是使得数据的均值维0,方差为1。
进行标准化处理,结果受所有数据的影响。(而不是像归一化处理,只是受到极值的影响)
标准化的原因在于如果有些特征的方差过大,则会主导目标函数从而使参数估计器无法正确地去学习其他特征。
标准化的过程为两步:去均值的中心化(均值变为0);方差的规模化(方差变为1)。
在sklearn.preprocessing中提供了一个scale的方法,可以实现以上功能
# 预处理数据的方法总结(使用sklearn-preprocessing)
from sklearn import preprocessing
import numpy as np
# 1. 标准化:去均值,方差规模化
# 创建一组特征数据,每一行表示一个样本,每一列表示一个特征
# Standardization标准化:将特征数据的分布调整成标准正太分布,也叫高斯分布,也就是使得数据的均值维0,方差为1.
# 标准化的原因在于如果有些特征的方差过大,则会主导目标函数从而使参数估计器无法正确地去学习其他特征。
# 标准化的过程为两步:去均值的中心化(均值变为0);方差的规模化(方差变为1)。
# 在sklearn.preprocessing中提供了一个scale的方法,可以实现以上功能。
x = np.array([[1., -1., 2.],
[2., 0., 0.],
[0., 1., -1.]])
# 将每一列特征标准化为标准正太分布,注意,标准化是针对每一列而言的
x_scale = preprocessing.scale(x)
x_scale
# preprocessing这个模块还提供了一个实用类StandarScaler,它可以在训练数据集上做了标准转换操作之后,把相同的转换应用到测试训练集中。
# 这是相当好的一个功能。可以对训练数据,测试数据应用相同的转换,以后有新的数据进来也可以直接调用,不用再重新把数据放在一起再计算一次了。
# 调用fit方法,根据已有的训练数据创建一个标准化的转换器
# 另外,StandardScaler()中可以传入两个参数:with_mean,with_std.这两个都是布尔型的参数,
# 默认情况下都是true,但也可以自定义成false.即不要均值中心化或者不要方差规模化为1.
scaler = preprocessing.StandardScaler().fit(x)
scaler
# 使用上面这个转换器去转换训练数据x,调用transform方法
scaler.transform(x)
# 好了,比如现在又来了一组新的样本,也想得到相同的转换
new_x = [[-1., 1., 0.]]
scaler.transform(new_x)
2/нормализация
把数据映射到[0,1]之间
归一化的结果受到极值的影响。
from sklearn import preprocessing
import numpy as np
# MinMaxScaler
# 在MinMaxScaler中是给定了一个明确的最大值与最小值。它的计算公式如下:
# X_std = (X - X.min(axis=0)) / (X.max(axis=0) - X.min(axis=0))
# X_scaled = X_std / (max - min) + min
# 以下这个例子是将数据规与[0,1]之间,每个特征中的最小值变成了0,最大值变成了1,请看:
min_max_scaler = preprocessing.MinMaxScaler()
x_minmax = min_max_scaler.fit_transform(x)
x_minmax
# 同样的,如果有新的测试数据进来,也想做同样的转换咋办呢?请看:
x_test = np.array([[-3., -1., 4.]])
x_test_minmax = min_max_scaler.transform(x_test)
x_test_minmax
3/ Регуляризация Нормализация
正则化是将样本在向量空间模型上的一个转换,经常被使用在分类与聚类中。
函数normalize()提供了一个快速有简单的方式在一个单向量上来实现这正则化的功能。
正则化有l1,l2等,这些都可以用上。
正则化可以解决过拟合的问题。
# 正则化Normalization
# 正则化是将样本在向量空间模型上的一个转换,经常被使用在分类与聚类中。
# 函数normalize 提供了一个快速有简单的方式在一个单向量上来实现这正则化的功能。
# 正则化有l1,l2等,这些都可以用上:
from sklearn import preprocessing
x_normalized = preprocessing.normalize(x,norm='l2')
# preprocessing这个模块还提供了一个实用类Normalizer,实用transform方法同样也可以对新的数据进行同样的转换
# 根据训练数据创建一个正则器
normalizer = preprocessing.Normalizer().fit(x)
normalizer
####################################################################
# 对训练数据进行正则
normalizer.transform(x)
###################################################################
# 对新的测试数据进行正则
normalizer.transform([[-1., 1., 0.]])
# normalize和Normalizer都既可以用在密集数组也可以用在稀疏矩阵(scipy.sparse)中
# 对于稀疏的输入数据,它会被转变成维亚索的稀疏行表征(具体请见scipy.sparse.csr_matrix)
###################################################################################
4/ Бинаризация — бинаризация признаков
特征的二值化是指将数值型的特征数据转换成布尔类型的值。
可以使用实用类Binarizer。
# 特征的二值化是指将数值型的特征数据转换成布尔类型的值。可以使用实用类Binarizer
# 默认是根据0来二值化,大于0的都标记为1,小于等于0的都标记为0。
from sklearn import preprocessing
import numpy as np
# 创建一组特征数据,每一行表示一个样本,每一列表示一个特征
x = np.array([[1., -1., 2.],
[2., 0., 0.],
[0., 1., -1.]])
binarizer = preprocessing.Binarizer().fit(x)
binarizer.transform(x)
##########################################################################
#当然也可以自己设置这个阀值,只需传出参数threshold即可
binarizer = preprocessing.Binarizer(threshold=1.5)
binarizer.transform(x)
##########################################################################
5/Горячее кодирование
# 4 为类别特征编码
# 我们知道特征可能是连续型的也可能是类别型的变量,比如说:
# [“male”, “female”], [“from Europe”, “from US”, “from Asia”], [“uses Firefox”, “uses Chrome”, “uses Safari”, “uses Internet Explorer”].
# 这些类别特征无法直接进入模型,它们需要被转换成整数来表征,比如:
# [“male”, “from US”, “uses Internet Explorer”] could be expressed as [0, 1, 3] while [“female”, “from Asia”, “uses Chrome”] would be [1, 2, 1].
# 然而上面这种表征的方式仍然不能直接为scikit-learn的模型所用,因为模型会把它们当成序列型的连续变量。
# 要想使得类别型的变量能最终被模型直接使用,可以使用one-of-k编码或者one-hot编码。
# 这些都可以通过OneHotEncoder实现,它可以将有n种值的一个特征变成n个二元的特征。
# 特征1中有(0,1)两个值,特征2中有(0,1,2)3个值,特征3中有(0,1,2,3)4个值,所以编码之后总共有9个二元特征。
enc = preprocessing.OneHotEncoder()
enc.fit([[0, 0, 3], [1, 1, 0], [0, 2, 1], [1, 0, 2]])
enc.transform([[0,1,3]]).toarray()
##########################################################################
# 但是呢,也会存在这样的情况,某些特征中可能对一些值有缺失,
# 比如明明有男女两个性别,样本数据中都是男性,这样就会默认被判别为我只有一类值。
# 这个时候我们可以向OneHotEncoder传如参数n_values,用来指明每个特征中的值的总个数
enc = preprocessing.OneHotEncoder(n_values=[2,3,4]) # 指明每个特征中的值的总个数分别为 2 3 4
enc.fit([[1, 2, 3], [0, 2, 0]])
enc.transform([[1,0,0]]).toarray()
#############################################################################
6/Дополнение к отсутствующему значению
# 5 弥补缺失数据
# 在scikit-learn的模型中都是假设输入的数据是数值型的,并且都是有意义的,如果有缺失数据是通过NAN,或者空值表示的话,就无法识别与计算了。
# 要弥补缺失值,可以使用均值,中位数,众数等等。Imputer这个类可以实现。请看:
import numpy as np
from sklearn.preprocessing import Imputer
imp = Imputer(missing_values='NaN',strategy='mean',axis=0) # 补充均值
imp.fit([[1, 2], [np.nan, 3], [7, 6]])
# 另外还有拉格朗日插值法
7/ Создание полиномиальных функций
有的时候线性的特征并不能做出完美的模型,于是我们会去尝试非线性。
非线性是建立在将特征进行多项式地展开上的。
比如将两个特征 (X_1, X_2),它的平方展开式便转换成5个特征(1, X_1, X_2, X_1^2, X_1X_2, X_2^2).
代码案例如下:
# 有的时候线性的特征并不能做出美的模型,于是我们会去尝试非线性。非线性是建立在将特征进行多项式地展开上的。
import numpy as np
from sklearn.preprocessing import PolynomialFeatures
# 自建一组3*2的样本
x = np.arange(6).reshape(3, 2)
# 创建2次方的多项式
# 比如将两个特征 (X_1, X_2),它的平方展开式便转换成5个特征(1, X_1, X_2, X_1^2, X_1X_2, X_2^2). 代码案例如下:
poly = PolynomialFeatures(2)
poly.fit_transform(x)