前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >机器学习特征数据预处理

机器学习特征数据预处理

作者头像
润森
发布2022-08-18 10:34:10
9730
发布2022-08-18 10:34:10
举报
文章被收录于专栏:毛利学Python毛利学Python
  • 标签处理
  • 特征处理
  • scikit-learn 特征处理
    • scikit LabelEncoder
    • scikit DictVectorizer
    • scikit OneHotEncoder
    • pandas get_dummies
  • 标准化
  • 归一化
  • Standardization and Min-Max scaling
  • plot

离散值处理

关于特征值离散化的相关内容下面直接进行举例,主要是标签处理、特征处理和OneHot。

代码语言:javascript
复制
import pandas as pd
df = pd.DataFrame([
            ['green', 'M', 10.1, 'class1'], 
            ['red', 'L', 13.5, 'class2'], 
            ['blue', 'XL', 15.3, 'class1']])

df.columns = ['color', 'size', 'prize', 'class label']
df

标签处理

通常我们会把字符型的标签转换成数值型的

代码语言:javascript
复制
class_mapping = {label:idx for idx,label in enumerate(set(df['class label']))}

df['class label'] = df['class label'].map(class_mapping)
df

特征处理

对于特征来说,我们一般可以做一个映射的字典

代码语言:javascript
复制
size_mapping = {
           'XL': 3,
           'L': 2,
           'M': 1}

df['size'] = df['size'].map(size_mapping)
df

我们还可以做这样的转换进行编码

代码语言:javascript
复制
color_mapping = {
           'green': (0,0,1),
           'red': (0,1,0),
           'blue': (1,0,0)}

df['color'] = df['color'].map(color_mapping)
df

对于数据,我们同样可以给它反变换回去

代码语言:javascript
复制
inv_color_mapping = {v: k for k, v in color_mapping.items()}
inv_size_mapping = {v: k for k, v in size_mapping.items()}
inv_class_mapping = {v: k for k, v in class_mapping.items()}

df['color'] = df['color'].map(inv_color_mapping)
df['size'] = df['size'].map(inv_size_mapping)
df['class label'] = df['class label'].map(inv_class_mapping)
df

scikit-learn 特征处理

scikit LabelEncoder

代码语言:javascript
复制
from sklearn.preprocessing import LabelEncoder

class_le = LabelEncoder()
df['class label'] = class_le.fit_transform(df['class label'])
df

反变换回去可以用这个函数 inverse_transform :

代码语言:javascript
复制
class_le.inverse_transform(df['class label'])

scikit DictVectorizer

使用 DictVectorizer将得到特征的字典

代码语言:javascript
复制
df.transpose().to_dict().values()
feature = df.iloc[:, :-1]
feature

对所有的数据都做了映射

代码语言:javascript
复制
from sklearn.feature_extraction import DictVectorizer
dvec = DictVectorizer(sparse=False)

X = dvec.fit_transform(feature.transpose().to_dict().values())
X

可以调用 get_feature_names 来返回新的列的名字,其中0和1就代表是不是这个属性.

代码语言:javascript
复制
pd.DataFrame(X, columns=dvec.get_feature_names())

scikit OneHotEncoder

OneHotEncoder 必须使用整数作为输入,所以得先预处理一下

代码语言:javascript
复制
color_le = LabelEncoder()
df['color'] = color_le.fit_transform(df['color'])

df
代码语言:javascript
复制
from sklearn.preprocessing import OneHotEncoder
ohe = OneHotEncoder(sparse=False)

X = ohe.fit_transform(df[['color']].values)
X

pandas get_dummies

Pandas库中同样有类似的操作,使用get_dummies也可以得到相应的特征

代码语言:javascript
复制
import pandas as pd
df = pd.DataFrame([
            ['green', 'M', 10.1, 'class1'], 
            ['red', 'L', 13.5, 'class2'], 
            ['blue', 'XL', 15.3, 'class1']])

df.columns = ['color', 'size', 'prize', 'class label']

size_mapping = {
           'XL': 3,
           'L': 2,
           'M': 1}
df['size'] = df['size'].map(size_mapping)

class_mapping = {label:idx for idx,label in enumerate(set(df['class label']))}
df['class label'] = df['class label'].map(class_mapping)


df

对整个DF使用get_dummies 将会得到新的列:

代码语言:javascript
复制
pd.get_dummies(df)

标准化与归一化

标准化

同样我们都需要对原始数据进行处理,少不了的就是 standardization (或者叫做 Z-score normalization)

要求 均值

\mu = 0

和标准差

\sigma = 1

转换公式如下:

z = \frac{x - \mu}{\sigma}

这个意义是十分重大的,想象一下,我们经常通过梯度下降来进行优化求解,公式一般如下,如果特征之间的数值差异太大,那么更新的结果肯定也会产生较大的差异,这是我们所不希望的。在最开始的时候,我们认为特征之间的重要程度的是一样,并不想偏袒哪个特征,所以这部预处理工作必做!

\Delta w_j = - \eta \frac{\partial J}{\partial w_j} = \eta \sum_i (t^{(i)} - o^{(i)})x^{(i)}_{j},

参数更新:

w_j := w_j + \Delta w_j,

归一化

另一种方法叫做 Min-Max scaling (或者叫做 "normalization"也就是我们常说的0-1归一化). 处理后的所有特征的值都会被压缩到 0到1区间上.这样做还可以抑制离群值对结果的影响. 归一化公式如下:

X_{norm} = \frac{X - X_{min}}{X_{max}-X_{min}}

Standardizing 和 Normalizing的Scikit-learn实现

葡萄酒数据集由3个不同的类组成,每一行对应一个特定的葡萄酒样本。类标签(1、2、3)列在第一列中,列2-14对应13个不同的属性(特征):

  1. Alcohol
  2. Malic acid
代码语言:javascript
复制
from sklearn.datasets import load_wine
wine = load_wine()
df= pd.concat([pd.DataFrame(wine.target),pd.DataFrame(wine["data"][:,:2],)],axis=1)
df.columns = ['Class label', 'Alcohol', 'Malic acid']

在数据中,Alcohol和Malic acid 衡量的标准应该是不同的,特征之间数值差异较大

Standardization and Min-Max scaling

代码语言:javascript
复制
from sklearn import preprocessing

std_scale = preprocessing.StandardScaler().fit(df[['Alcohol', 'Malic acid']])
df_std = std_scale.transform(df[['Alcohol', 'Malic acid']])

minmax_scale = preprocessing.MinMaxScaler().fit(df[['Alcohol', 'Malic acid']])
df_minmax = minmax_scale.transform(df[['Alcohol', 'Malic acid']])

print('Mean after standardization:\nAlcohol={:.2f}, Malic acid={:.2f}'
      .format(df_std[:,0].mean(), df_std[:,1].mean()))
print('\nStandard deviation after standardization:\nAlcohol={:.2f}, Malic acid={:.2f}'
      .format(df_std[:,0].std(), df_std[:,1].std()))
代码语言:javascript
复制
print('Min-value after min-max scaling:\nAlcohol={:.2f}, Malic acid={:.2f}'
      .format(df_minmax[:,0].min(), df_minmax[:,1].min()))
print('\nMax-value after min-max scaling:\nAlcohol={:.2f}, Malic acid={:.2f}'
      .format(df_minmax[:,0].max(), df_minmax[:,1].max()))

plot

代码语言:javascript
复制
from matplotlib import pyplot as plt

def plot():
    plt.figure(figsize=(8,6))

    plt.scatter(df['Alcohol'], df['Malic acid'], 
            color='green', label='input scale', alpha=0.5)

    plt.scatter(df_std[:,0], df_std[:,1], color='red', 
            label='Standardized [$N  (\mu=0, \; \sigma=1)$]', alpha=0.3)

    plt.scatter(df_minmax[:,0], df_minmax[:,1], 
            color='blue', label='min-max scaled [min=0, max=1]', alpha=0.3)

    plt.title('Alcohol and Malic Acid content of the wine dataset')
    plt.xlabel('Alcohol')
    plt.ylabel('Malic Acid')
    plt.legend(loc='upper left')
    plt.grid()
    
    plt.tight_layout()

plot()
plt.show()

我们将原始的和变换后都放到了同一个图上,观察下结果吧!接下来我们再看看数据是否被打乱了呢?

代码语言:javascript
复制
fig, ax = plt.subplots(3, figsize=(6,14))

for a,d,l in zip(range(len(ax)), 
               (df[['Alcohol', 'Malic acid']].values, df_std, df_minmax),
               ('Input scale', 
                'Standardized [$N  (\mu=0, \; \sigma=1)$]', 
                'min-max scaled [min=0, max=1]')
                ):
    for i,c in zip(range(1,4), ('red', 'blue', 'green')):
        ax[a].scatter(d[df['Class label'].values == i, 0], 
                  d[df['Class label'].values == i, 1],
                  alpha=0.5,
                  color=c,
                  label='Class %s' %i
                  )
    ax[a].set_title(l)
    ax[a].set_xlabel('Alcohol')
    ax[a].set_ylabel('Malic Acid')
    ax[a].legend(loc='upper left')
    ax[a].grid()
    
plt.tight_layout()

plt.show()

在机器学习中,如果我们对训练集做了上述处理,那么同样的对测试集也必须要经过相同的处理

代码语言:javascript
复制
std_scale = preprocessing.StandardScaler().fit(X_train)
X_train = std_scale.transform(X_train)
X_test = std_scale.transform(X_test)
本文参与 腾讯云自媒体分享计划,分享自微信公众号。
原始发表:2021-11-10,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 小刘IT教程 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 离散值处理
    • 标签处理
      • 特征处理
        • scikit-learn 特征处理
          • scikit LabelEncoder
          • scikit DictVectorizer
          • scikit OneHotEncoder
          • pandas get_dummies
      • 标准化与归一化
        • 标准化
          • 归一化
          • Standardizing 和 Normalizing的Scikit-learn实现
            • Standardization and Min-Max scaling
              • plot
              领券
              问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档