機器學習 數據表達與特徵工程

數據表達與特徵工程

1、簡介

在機器學習裏面,特徵的選取與特徵數據預處理十分重要,特徵的準確性直接決定最終模型的準確性,而選擇更好的訓練模型只能爲了更好的逼近預期值。

特徵工程就是對於原始數據進行數據預處理, 儘可能把可以把後續模型建立需要的特徵提取出來。並把原始數據規整化,爲後續建模做準備。

類型特徵(categorical features):有些特徵值爲字符串,比如:地理位置有的是 東南, 有的是 西北,我們將這類特徵稱作爲類型特徵。

連續特徵(continuous features):數值類型的特徵稱爲連續特徵。

特徵的提取與特徵數值化轉化,這部分是內容充滿了挑戰與技術含量,需要研究的價值很大。

2、啞變量轉化類型特徵

在此解釋一下什麼是啞變量(Dummy Variables),啞變量也稱爲虛擬變量,是一種在統計學和經濟學領域非常常用的,用來將某些類型轉化爲二值變量的方法,在迴歸分析中使用尤其廣泛。

特徵二值化又稱爲熱編碼,熱編碼的優勢見如下鏈接

熱編碼 One-Hot encoding優勢分析

1、對字符串類型特徵 Direction 做二值化處理:

 第一種:sklearn中LabelEncoder() + OneHotEncoder()

from sklearn.preprocessing import LabelEncoder
from sklearn.preprocessing import OneHotEncoder
# 得到二值化的特徵向量
direction = OneHotEncoder(sparse=False).fit_transform(LabelEncoder().fit_transform(testdata['Direction']).reshape(-1,1))
# 將二值化的特徵向量轉化爲DataFrame類型
direction = pd.DataFrame(direction, columns=['direction_west','direction_north','direction_south'])

 第二種:sklearn中直接調用 LabelBinarizer()或MultiLabelBinarizer(),用於數字和字符串都可以

from sklearn.preprocessing import LabelBinarizer
# 將單特徵直接二值化爲二維向量
direction_binarlizer = LabelBinarizer().fit_transform(testdata['Direction'])
direction = pd.DataFrame(pet_binarlizer,columns=['direction_west','direction_north','direction_south'])
# 將多特徵直接二值化爲二維向量,適用於一次進行多組特徵轉化
add_df = MultiLabelBinarizer().fit_transform(df[['Direction', 'Elevator']].values)

第三種: pandas中調用get_dummies直接進行二值化編碼

             優勢:多維和單維特徵都可以一次性轉化、本身就是pandas模塊與DataFrame兼容好、能根據用戶指定自動生成編碼後的變量名

import pandas as pd
df = pd.read_csv('new_house.csv', encoding='utf-8')
# 對單列數據進行二值化操作,生成一個series
add_df = pd.get_dummies(df[['Direction']])
# 將二值化特徵與原特徵融合
df = pd.concat([df, add_df], axis=1)
# 對多列數據進行二值化操作,prefix可以用來替換生成特徵前綴名字,add_df爲一個DataFrame對象
add_df = pd.get_dummies(df, columns=['Direction', 'Elevator'], prefix=['col1', 'col2'])

注意:以上二值化操作都不會對特徵值爲數值的進行轉化 

 第四種: sklearn中調用 Binarizer 根據閾值將數值型轉化爲二進制,注意只針對數值轉化

import pandas as pd
import numpy as np
from sklearn.preprocessing import Binarizer

df = pd.DataFrame(np.arange(12).reshape(4,3),columns=['A','B','C'])
# threshold=4代表的含義爲將值大於5的用1代替,小於5的用0代替
binarize = Binarizer(threshold=4).fit_transform(df)

 3、數值化編碼

可以將數據(類別型或者數值型都可以)轉換爲一個整數值,比如講高中低轉換爲0,1,2;假設特徵的取值類別有n種,那麼轉換到的範圍就是[0:n];LabelEncoder的輸入必須是個一維的數組,如Series這種格式,如果是DataFrame對象則會報錯

 from sklearn.preprocessing import LabelEncoder
a = LabelEncoder().fit_transform(testdata['Direction'])

4、code示例-利用SVR進行房價預測

import pandas as pd
import numpy as np
from sklearn.preprocessing import LabelBinarizer
from sklearn.preprocessing import StandardScaler
from sklearn.preprocessing import Binarizer
from sklearn.model_selection import train_test_split
from sklearn.svm import SVR
from sklearn.externals import joblib


# 從CSV獲取數據
df = pd.read_csv('new_house.csv', encoding='utf-8')  # nrows設置讀取數據的行數

# 刪除無用特徵id
df = df.drop(['Id'], axis=1)

# 去除包含有空值的行數據,也就是去除噪音,增強數據的準確性
df.dropna(axis=0, how='any', inplace=True)

# 抽取target目標數據
y = df.pop('Price')

# 移動Price到末尾列
# df.insert(len(df.columns), 'Price', price)
# 抽取數值特徵數據
X = df[['Floor', 'Size', 'Year']].values

# 進行特徵數值化處理
# 1、標籤數值化,適用於將類別(也就是文字性的東西轉化爲數值),標籤類型二值化
features = ['Direction', 'District', 'Elevator', 'Garden', 'Layout', 'Region', 'Renovation']
for feature in features:
    values = LabelBinarizer().fit_transform(df[feature].values)
    values = np.stack(values)  # 將一維行數據轉化爲二維列數據
    X = np.concatenate((X, values), axis=1)

# 隨機拆分訓練數據和測試數據集,test_size控制測試數據集的拆分比列,random_state爲隨機拆分的隨機數
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.25, random_state=8)

# 對數值進行正太分佈處理,將所有的數據的特徵值轉化爲均值爲0,而方差爲1的狀態,這樣就可以確保數據的大小都是一致的,這樣有利於模型的訓練
# 對數據進行預處理的好處,可以提升模型的準確率
scaler = StandardScaler()
scaler.fit(X_train)

# 模型訓練
X_train_scaled = scaler.transform(X_train)
X_test_scaled = scaler.transform(X_test)

# 套用不同的核函數,觀察不同核函數對模型的預測準確率的影響
for kernel in ['rbf']:
    svr = SVR(kernel=kernel, C=100, gamma=0.1)
    svr.fit(X_train_scaled, y_train)
    print(kernel, "核函數的模型訓練得分:{:.3f}".format(svr.score(X_train_scaled, y_train)))
    print(kernel, "核函數的模型測試得分:{:.3f}".format(svr.score(X_test_scaled, y_test)))

    joblib.dump(svr, 'train_model_{}.m'.format(kernel))
    # 加載訓練模型
    # svr = joblib.load('train_model_rbf.m')

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章