sklearn.preprocessing.
scale
(X, axis=0, with_mean=True, with_std=True, copy=True)
X | 用来标准化的数据(数组或者稀疏矩阵) |
axis | 0表示对一列去做相同的操作,1表示对一行去做相同的操作 |
with_mean | 要均值中心化(true) |
with_std | 要方差规模化(true) |
标准化的过程为两步:去均值的中心化(均值变为0);方差的规模化(方差变为1)。
from sklearn import preprocessing
import numpy as np
# 创建一组特征数据,每一行表示一个样本,每一列表示一个特征
x = np.array([[1., -1., 2.],
[2., 0., 0.],
[0., 1., -1.]])
# 将每一列特征标准化为标准正太分布,注意,标准化是针对每一列而言的
x_scale = preprocessing.scale(x)
x_scale
>>> array([[ 0. , -1.22474487, 1.33630621],
[ 1.22474487, 0. , -0.26726124],
[-1.22474487, 1.22474487, -1.06904497]])
# 可以查看标准化后的数据的均值与方差,已经变成0,1了
x_scale.mean(axis=0)
>>> array([ 0., 0., 0.])
x_scale.std(axis=0)
>>> array([ 1., 1., 1.])
# axis=1表示对每一行去做这个操作,axis=0表示对每一列做相同的这个操作
x_scale.mean(axis=1)
>>> array([ 0.03718711, 0.31916121, -0.35634832])
标准化是依照特征矩阵(每一列是用同一个特征的不同取值)的列处理数据,其通过求z-score的方法,将样本的每个特征的值转换到同一量纲下。
归一化是依照特征矩阵(每一行是不同特征的取值)的行处理数据,其目的在于样本向量在点乘运算或其他核函数计算相似性时,拥有统一的标准,也就是说都转化为“单位向量”。
sklearn.preprocessing.
normalize
(X, norm=’l2’, axis=1, copy=True, return_norm=False)
Normalization各个样本归一化为norm为1的正态分布
函数 normalize 提供了一个简单的方法来操作类似数组的数据集,使用l1或l2范式(norm参数)
x = np.array([[1., -1., 2.],
[2., 0., 0.],
[0., 1., -1.]])
X_normalized = preprocessing.normalize(x, norm='l2')
print(X_normalized)
>>> [[ 0.40824829 -0.40824829 0.81649658]
[ 1. 0. 0. ]
[ 0. 0.70710678 -0.70710678]]
归一化至[0, 1]
x = np.array([[1., -1., 2.],
[2., 0., 0.],
[0., 1., -1.]])
min_max_scaler = preprocessing.MinMaxScaler()
X_train_minmax = min_max_scaler.fit_transform(x)
print(X_train_minmax)
>>> [[0.5 0. 1. ]
[1. 0.5 0.33333333]
[0. 1. 0. ]]
# 查看scaler的属性
min_max_scaler.scale_
array([ 0.5 , 0.5 , 0.33...])
min_max_scaler.min_
array([ 0. , 0.5 , 0.33...])
特征的二值化是指将数值型的特征数据转换成布尔类型的值。可以使用实用类Binarizer。默认是根据0来二值化,大于0的都标记为1,小于等于0的都标记为0。
binarizer = preprocessing.Binarizer().fit(x)
print(binarizer.transform(x))
>>> [[1. 0. 1.]
[1. 0. 0.]
[0. 1. 0.]]
OneHotEncoder(categorical_features='all', dtype=<... 'float'>,
handle_unknown='error', n_values='auto', sparse=True)
要想使得类别型的变量能最终被模型直接使用,可以使用one-of-k编码或者one-hot编码。这些都可以通过OneHotEncoder(独热编码)实现,它可以将有n种值的一个特征变成n个二元的特征。默认情况下,n值时通过数据集自动推断出来的。例如,数据集中有2种性别,三种可能的地方,4中可能的浏览器。然后在编码时,在9列的array数组中,前2个数字编码性别,接下来3个数字编码地方,最后4个数字编码浏览器。对于离散的特征基本就是按照one-hot(独热)编码,该离散特征有多少取值,就用多少维来表示该特征。将离散型特征使用one-hot编码,会让特征之间的距离计算更加合理。离散特征进行one-hot编码后,编码后的特征,其实每一维度的特征都可以看做是连续的特征。就可以跟对连续型特征的归一化方法一样,对每一维特征进行归一化。比如归一化到[-1,1]或归一化到均值为0,方差为1。
from sklearn import preprocessing
enc = preprocessing.OneHotEncoder()
enc.fit([[0, 0, 3], [1, 1, 0], [0, 2, 1], [1, 0, 2]]) # fit来学习编码
enc.transform([[0, 1, 3]]).toarray() # 进行编码
>>> [[1. 0. 0. 1. 0. 0. 0. 0. 1.]]
# 但是呢,也会存在这样的情况,某些特征中可能对一些值有缺失,
# 比如明明有男女两个性别,样本数据中都是男性,这样就会默认被判别为我只有一类值。
# 这个时候我们可以向OneHotEncoder传如参数n_values,用来指明每个特征中的值的总个数
enc = preprocessing.OneHotEncoder(n_values=[2,3,4]) # 指明每个特征中的值的总个数分别为 2 3 4
# 对象enc的n_values_成员变量,记录着每一个属性的最大取值数目
print(enc.n_values_) # 好像已经弃用
[2 3 4]
feature_indices_:每个定性特征的有效值范围,例如第i个定性特征,其有效值范围为feature_indices_[i]至feature_indices_[i+1],sklearn官方文档在此描述有误,
该数组的长度应为n_features+1。在上例中,feature_indices_等于(0,3,8)。
故下标为0的定性特征,其有效值范围为大于0小于3,则有效值为1和2;下标为1的定性特征,
其有效值范围为大于3小于8,则有效值为5和7。下标为0的定性特征,其两个真实有效值为1-0=1和2-0=2;
下标为1的定性特征,其两个真实有效值为5-3=2和7-3=4。这样一来就可以得到(1,2,2,4)的真实有效值了。
针对上例,数据矩阵是4*3,即4个数据,3个特征维度
0 0 3 第一列为第一个特征维度,有两种取值,分别为0和1,所以对应的编码方式为10、01
1 1 0 第二列为第二个特征维度,有三种取值,分别为0、1和2,所以对应的编码方式为100、010、001
0 2 1 第三列为第三个特征维度,有四种取值,分别为0、1、2和3,所以对应的编码方式为1000、0100、0010、0001
1 0 2
要进行编码的参数[0, 1, 3],0->10, 1->010, 3->0001,所以是100100001
>>> genders = ['female', 'male']
>>> locations = ['from Africa', 'from Asia', 'from Europe', 'from US']
>>> browsers = ['uses Chrome', 'uses Firefox', 'uses IE', 'uses Safari']
>>> enc = preprocessing.OneHotEncoder(categories=[genders, locations, browsers])
>>> # Note that for there are missing categorical values for the 2nd and 3rd
>>> # feature
>>> X = [['male', 'from US', 'uses Safari'], ['female', 'from Europe', 'uses Firefox']]
>>> enc.fit(X)
OneHotEncoder(categorical_features=None,
categories=[...],
dtype=<... 'numpy.float64'>, handle_unknown='error',
n_values=None, sparse=True)
>>> enc.transform([['female', 'from Asia', 'uses Chrome']]).toarray()
array([[1., 0., 0., 1., 0., 0., 1., 0., 0., 0.]])
在scikit-learn的模型中都是假设输入的数据是数值型的,并且都是有意义的,如果有缺失数据是通过NAN,或者空值表示的话,就无法识别与计算了。要弥补缺失值,可以使用均值,中位数,众数等等。Imputer这个类可以实现。对于数组中是否存在nan可以使用np.isnan()来判定。
stratege="constant"的时候给定fill_value就是用常量填补
>>> import numpy as np
>>> from sklearn.impute import SimpleImputer
>>> imp = SimpleImputer(missing_values=np.nan, strategy='mean')
>>> imp.fit([[1, 2], [np.nan, 3], [7, 6]])
SimpleImputer(copy=True, fill_value=None, missing_values=nan, strategy='mean', verbose=0)
>>> X = [[np.nan, 2], [6, np.nan], [7, 6]]
>>> print(imp.transform(X))
[[4. 2. ]
[6. 3.666...]
[7. 6. ]]
#################过时
from sklearn.preprocessing import Imputer
imp = Imputer(missing_values='NaN', strategy='mean', axis=0)
imp.fit([[1, 2], [np.nan, 3], [7, 6]])
x = [[np.nan, 2], [6, np.nan], [7, 6]]
print(imp.transform(x))
#或者
#imp.fit(x)
#imp.transform(x)
[[4. 2. ]
[6. 3.66666667]
[7. 6. ]]
有空格的的数据
#含有空格的数据
tem='1,2,3, ,3,4,5,6,7,8, ,9'
print tem
#替换空格字符
tem = tem.replace(' ','nan').split(',')
print tem
#将数据转换成浮点型矩阵形式
x = np.array(tem,dtype = float).reshape((4,3))
print x
1,2,3, ,3,4,5,6,7,8, ,9
['1', '2', '3', 'nan', '3', '4', '5', '6', '7', '8', 'nan', '9']
[[ 1. 2. 3.]
[ nan 3. 4.]
[ 5. 6. 7.]
[ 8. nan 9.]]
Imputer().fit_transform(x)
array([[ 1. , 2. , 3. ],
[ 4.66666667, 3. , 4. ],
[ 5. , 6. , 7. ],
[ 8. , 3.66666667, 9. ]])
Imputer()的参数有:
1. missing_values:默认是((default=”NaN”))
2. strategy :string字符格式, optional (default=”mean”),一般有mean(均值),median(中位数),most_frequent(众数)
3. axis:轴向,默认是(列向,axis =0),行是(axis=1)
可通过help指令显示对Imputer的解释 help(Imputer())
通过考虑输入数据的非线性特征来增加模型的复杂度是很有用的。一个简单常用的方法是多项式特征,它可以得到特征的高阶和相互作用项。
下面的代码将(X1, X2)转化为(1, X1, X2, X1^2, X1X2, X2^2)
from (X1,X2,X3) to (1,X1,X2,X3,X1X2,X1X3,X2X3,X1X2X3). interaction_only=True 没有自身的平方
>>> import numpy as np
>>> from sklearn.preprocessing import PolynomialFeatures
>>> X = np.arange(6).reshape(3, 2)
>>> X
array([[0, 1],
[2, 3],
[4, 5]])
>>> poly = PolynomialFeatures(2)
>>> poly.fit_transform(X)
array([[ 1., 0., 1., 0., 0., 1.],
[ 1., 2., 3., 4., 6., 9.],
[ 1., 4., 5., 16., 20., 25.]])
>>> X = np.arange(9).reshape(3, 3)
>>> X
array([[0, 1, 2],
[3, 4, 5],
[6, 7, 8]])
>>> poly = PolynomialFeatures(degree=3, interaction_only=True)
>>> poly.fit_transform(X)
array([[ 1., 0., 1., 2., 0., 0., 2., 0.],
[ 1., 3., 4., 5., 12., 15., 20., 60.],
[ 1., 6., 7., 8., 42., 48., 56., 336.]])