機(jī)器學(xué)習(xí)的模型訓(xùn)練越來越自動(dòng)化,但特征工程還是一個(gè)漫長的手動(dòng)過程,依賴于專業(yè)的領(lǐng)域知識,直覺和數(shù)據(jù)處理。而特征選取恰恰是機(jī)器學(xué)習(xí)重要的先期步驟,雖然不如模型訓(xùn)練那樣能產(chǎn)生直接可用的結(jié)果。本文作者將使用Python的featuretools庫進(jìn)行自動(dòng)化特征工程的示例。
創(chuàng)新互聯(lián)建站專注于盧氏企業(yè)網(wǎng)站建設(shè),響應(yīng)式網(wǎng)站開發(fā),商城建設(shè)。盧氏網(wǎng)站建設(shè)公司,為盧氏等地區(qū)提供建站服務(wù)。全流程按需定制,專業(yè)設(shè)計(jì),全程項(xiàng)目跟蹤,創(chuàng)新互聯(lián)建站專業(yè)和態(tài)度為您提供的服務(wù)
機(jī)器學(xué)習(xí)越來越多地從手動(dòng)設(shè)計(jì)模型轉(zhuǎn)變?yōu)槭褂肏20,TPOT和auto-sklearn等工具來自動(dòng)優(yōu)化的渠道。這些庫以及隨機(jī)搜索等方法旨在通過查找數(shù)據(jù)集的最優(yōu)模型來簡化模型選擇和轉(zhuǎn)變機(jī)器學(xué)習(xí)的部分,幾乎不需要人工干預(yù)。然而,特征工程幾乎完全是人工,這無疑是機(jī)器學(xué)習(xí)管道中更有價(jià)值的方面。
特征工程也稱為特征創(chuàng)建,是從現(xiàn)有數(shù)據(jù)構(gòu)建新特征以訓(xùn)練機(jī)器學(xué)習(xí)模型的過程。這個(gè)步驟可能比實(shí)際應(yīng)用的模型更重要,因?yàn)闄C(jī)器學(xué)習(xí)算法只從我們提供的數(shù)據(jù)中學(xué)習(xí),然而創(chuàng)建與任務(wù)相關(guān)的特征絕對是至關(guān)重要的。
通常,特征工程是一個(gè)漫長的手動(dòng)過程,依賴于專業(yè)的領(lǐng)域知識,直覺和數(shù)據(jù)處理。這個(gè)過程可能非常繁瑣,而且最終的特征將受到人類主觀性和時(shí)間的限制。自動(dòng)化特征工程旨在通過從數(shù)據(jù)集中自動(dòng)創(chuàng)建許多候選特征來幫助數(shù)據(jù)科學(xué)家,并從中可以選擇最佳特征用于訓(xùn)練。
在本文中,我們將使用Python 的featuretools庫進(jìn)行自動(dòng)化特征工程的示例。我們將使用示例數(shù)據(jù)集來演示基礎(chǔ)知識。
特征工程基礎(chǔ)
特征工程意味著從現(xiàn)有數(shù)據(jù)中構(gòu)建額外特征,這些數(shù)據(jù)通常分布在多個(gè)相關(guān)表中。特征工程需要從數(shù)據(jù)中提取相關(guān)信息并將其放入單個(gè)表中,然后可以使用該表來訓(xùn)練機(jī)器學(xué)習(xí)模型。
構(gòu)建特征的過程非常地耗時(shí),因?yàn)槊總€(gè)特征的構(gòu)建通常需要一些步驟來實(shí)現(xiàn),尤其是使用多個(gè)表中的信息時(shí)。我們可以將特征創(chuàng)建的步驟分為兩類:轉(zhuǎn)換和聚合。讓我們看幾個(gè)例子來了解這些概念的實(shí)際應(yīng)用。
轉(zhuǎn)換作用于單個(gè)表(從Python角度來看,表只是一個(gè)Pandas數(shù)據(jù)框),它通過一個(gè)或多個(gè)現(xiàn)有的列創(chuàng)建新特征。
例如,如果我們有如下客戶表。
我們可以通過查找joined列的月份或是獲取income列的自然對數(shù)來創(chuàng)建特征。這些都是轉(zhuǎn)換,因?yàn)樗鼈儍H使用來自一個(gè)表的信息。
import pandas as pd
# Group loans by client id and calculate mean, max, min of loans
stats = loans.groupby('client_id')['loan_amount'].agg(['mean', 'max', 'min'])
stats.columns = ['mean_loan_amount', 'max_loan_amount', 'min_loan_amount']
# Merge with the clients dataframe
stats = clients.merge(stats, left_on = 'client_id', right_index=True, how = 'left')
stats.head(10)
另一方面,聚合作用于多個(gè)表,并使用一對多的關(guān)系對觀測值進(jìn)行分組,然后計(jì)算統(tǒng)計(jì)數(shù)據(jù)。例如,如果我們有另一個(gè)包含客戶貸款的信息表格,其中每個(gè)客戶可能有多筆貸款,我們可以計(jì)算每個(gè)客戶的貸款的平均值,最大值和最小值等統(tǒng)計(jì)數(shù)據(jù)。
此過程包括通過客戶信息對貸款表進(jìn)行分組,計(jì)算聚合,然后將結(jié)果數(shù)據(jù)合并到客戶數(shù)據(jù)中。以下是我們?nèi)绾问褂肞andas庫在Python中執(zhí)行此操作。
這些操作本身并不困難,但如果我們有數(shù)百個(gè)變量分布在幾十個(gè)表中,那么這個(gè)過程要通過手工完成是不可行的。理想情況下,我們需要一種能夠跨多個(gè)表自動(dòng)執(zhí)行轉(zhuǎn)換和聚合的解決方案,并將結(jié)果數(shù)據(jù)合并到一個(gè)表中。盡管Pandas庫是一個(gè)很好的資源,但通過我們手工完成的數(shù)據(jù)操作是有限的。
Featuretools
幸運(yùn)的是,featuretools正是我們正在尋找的解決方案。這個(gè)開源Python庫將自動(dòng)從一組相關(guān)表中創(chuàng)建許多特征。Featuretools基于一種稱為“深度特征合成”的方法,這個(gè)名字聽起來比實(shí)際的用途更令人印象深刻
深度特征合成實(shí)現(xiàn)了多重轉(zhuǎn)換和聚合操作(在featuretools的詞匯中稱為特征基元),通過分布在許多表中的數(shù)據(jù)來創(chuàng)建特征。像機(jī)器學(xué)習(xí)中的大多數(shù)觀念一樣,它是建立在簡單概念基礎(chǔ)上的復(fù)合型方法。通過一次學(xué)習(xí)一個(gè)構(gòu)造塊的示例,我們就會(huì)容易理解這種強(qiáng)大的方法。
首先,我們來看看我們的示例數(shù)據(jù)。 我們已經(jīng)看到了上面的一些數(shù)據(jù)集,完整的表集合如下:
客戶:即有關(guān)信貸聯(lián)盟中客戶的基本信息。每個(gè)客戶在此數(shù)據(jù)框中只有一行。
貸款:即客戶貸款。每項(xiàng)貸款在此數(shù)據(jù)框中只有自己單獨(dú)一行的記錄,但客戶可能有多項(xiàng)貸款。
付款:即支付貸款。 每筆支付只有一行記錄,但每筆貸款都有多筆支付記錄。
如果我們有機(jī)器學(xué)習(xí)目標(biāo),例如預(yù)測客戶是否將償還未來貸款,我們希望將有關(guān)客戶的所有信息組合到一個(gè)表中。這些表是相關(guān)的(通過client_id和loan_id變量),目前我們可以手動(dòng)完成一系列轉(zhuǎn)換和聚合過程。然而,不久之后我們就可以使用featuretools來自動(dòng)化該過程。
實(shí)體和實(shí)體集
featuretools的前兩個(gè)概念是實(shí)體和實(shí)體集。實(shí)體只是一個(gè)表(如果用Pandas庫的概念來理解,實(shí)體是一個(gè)DataFrame(數(shù)據(jù)框))。
EntitySet(實(shí)體集)是表的集合以及它們之間的關(guān)系??梢詫?shí)體集視為另一個(gè)Python數(shù)據(jù)結(jié)構(gòu),該結(jié)構(gòu)具有自己的方法和屬性。)
我們可以使用以下命令在featuretools中創(chuàng)建一個(gè)空實(shí)體集:
import featuretools as ft
# Create new entityset
es = ft.EntitySet(id = 'clients')
現(xiàn)在我們添加實(shí)體。每個(gè)實(shí)體都必須有一個(gè)索引,該索引是一個(gè)包含所有唯一元素的列。也就是說,索引中的每個(gè)值只能出現(xiàn)在表中一次。
clients數(shù)據(jù)框中的索引是client_id,因?yàn)槊總€(gè)客戶在此數(shù)據(jù)框中只有一行。 我們使用以下語法將一個(gè)現(xiàn)有索引的實(shí)體添加到實(shí)體集中:
# Create an entity from the client dataframe
# This dataframe already has an index and a time index
es = es.entity_from_dataframe(entity_id = 'clients', dataframe = clients, index = 'client_id', time_index = 'joined')
loans數(shù)據(jù)框還具有唯一索引loan_id,并且將其添加到實(shí)體集的語法與clients相同。但是,對于payments數(shù)據(jù)框,沒有唯一索引。當(dāng)我們將此實(shí)體添加到實(shí)體集時(shí),我們需要傳入?yún)?shù)make_index = True并指定索引的名稱。此外,雖然featuretools會(huì)自動(dòng)推斷實(shí)體中每列的數(shù)據(jù)類型,但我們可以通過將列類型的字典傳遞給參數(shù)variable_types來覆蓋它。
# Create an entity from the payments dataframe
# This does not yet have a unique index
es = es.entity_from_dataframe(entity_id = 'payments',
dataframe = payments,
variable_types = {'missed': ft.variable_types.Categorical},
make_index = True,
index = 'payment_id',
time_index = 'payment_date')
對于這個(gè)數(shù)據(jù)框,即使missed 的類型是一個(gè)整數(shù),但也不是一個(gè)數(shù)字變量,因?yàn)樗荒苋?個(gè)離散值,所以我們告訴featuretools將缺失數(shù)據(jù)視作是一個(gè)分類變量。將數(shù)據(jù)框添加到實(shí)體集后,我們檢查它們中的任何一個(gè):
使用我們指定的修改模型能夠正確推斷列類型。接下來,我們需要指定實(shí)體集中的表是如何相關(guān)的。
數(shù)據(jù)表之間的關(guān)系
考慮兩張數(shù)據(jù)表之間關(guān)系的最佳方式是用父對子的類比 。父與子是一對多的關(guān)系:每個(gè)父母可以有多個(gè)孩子。在數(shù)據(jù)表的范疇中,父表的每一行代表一位不同的父母,但子表中的多行代表的多個(gè)孩子可以對應(yīng)到父表中的同一位父母。
例如,在我們的數(shù)據(jù)集中,clients客戶數(shù)據(jù)框是loan貸款數(shù)據(jù)框的父級,因?yàn)槊總€(gè)客戶在客戶表中只有一行,但貸款可能有多行。
同樣,貸款loan數(shù)據(jù)是支付payments數(shù)據(jù)的父級,因?yàn)槊抗P貸款都有多筆付款。父級數(shù)據(jù)表通過共享變量與子級數(shù)據(jù)表關(guān)聯(lián)。當(dāng)我們執(zhí)行聚合操作時(shí),我們通過父變量對子表進(jìn)行分組,并計(jì)算每個(gè)父項(xiàng)的子項(xiàng)之間的統(tǒng)計(jì)數(shù)據(jù)。
我們只需要指明將兩張數(shù)據(jù)表關(guān)聯(lián)的那個(gè)變量,就能用featuretools來建立表格見的關(guān)系 。
客戶clients數(shù)據(jù)表和貸款loans數(shù)據(jù)表通過變量client_id
相互關(guān)聯(lián),而貸款loans數(shù)據(jù)表和支付payments數(shù)據(jù)表則通過變量loan_id相互關(guān)聯(lián)。以下是建立關(guān)聯(lián)并將其添加到entiytset的語法:
# Relationship between clients and previous loans
r_client_previous = ft.Relationship(es['clients']['client_id'],
es['loans']['client_id'])
# Add the relationship to the entity set
es = es.add_relationship(r_client_previous)
# Relationship between previous loans and previous payments
r_payments = ft.Relationship(es['loans']['loan_id'],
es['payments']['loan_id'])
# Add the relationship to the entity set
es = es.add_relationship(r_payments)
es
現(xiàn)在,在entityset中包含了三張數(shù)據(jù)表,以及三者間的關(guān)系。在添加entities并建立關(guān)聯(lián)后,我們的entityset就算完成了,可以開始建立特征量了。
特征基元
在我們完全深入進(jìn)行特征合成之前,我們需要了解特征基元。我們已經(jīng)知道它們是什么了,但我們剛剛用不同的名字來稱呼它們!這些只是我們用來形成新功能的基本操作:
聚合:基于父表與子表(一對多)關(guān)系完成的操作,按父表分組,并計(jì)算子表的統(tǒng)計(jì)數(shù)據(jù)。一個(gè)例子是通過client_id對貸款loan表進(jìn)行分組,并找到每個(gè)客戶的最大貸款額。
轉(zhuǎn)換:在單個(gè)表上對一列或多列執(zhí)行的操作。一個(gè)例子是在一個(gè)表中取兩個(gè)列之間的差異或取一列的絕對值。
在featuretools中使用這些基元本身或堆疊多個(gè)基元,來創(chuàng)建新功能。下面是featuretools中一些特征基元的列表(我們也可以定義自定義基元)
這些原語可以單獨(dú)使用,也可以組合使用來創(chuàng)建特征量。要使用指定的基元制作特征,我們使用ft.dfs函數(shù)(代表深度特征合成)。我們傳入entityset,target_entity,這是我們要添加特征的表,選擇的trans_primitives(轉(zhuǎn)換)和agg_primitives(聚合):
# Create new features using specified primitives
features, feature_names = ft.dfs(entityset = es, target_entity = 'clients',
agg_primitives = ['mean', 'max', 'percent_true', 'last'],
trans_primitives = ['years', 'month', 'subtract', 'divide'])
結(jié)果是每個(gè)客戶端的新特征數(shù)據(jù)框(因?yàn)槲覀兪箍蛻舳顺蔀閠arget_entity)。例如,我們有每個(gè)客戶加入的月份,這是由轉(zhuǎn)換特征基元生成的:
我們還有許多聚合基元,例如每個(gè)客戶的平均付款金額:
我們還有許多聚合基元,例如每個(gè)客戶的平均付款金額:
深度特征合成
我們現(xiàn)在已經(jīng)做好準(zhǔn)備來理解深度特征合成(dfs)。實(shí)際上,我們已經(jīng)在之前的函數(shù)調(diào)用中執(zhí)行了dfs!深度特征僅僅是堆疊多個(gè)基元的特征,而dfs是制作這些特征的過程名稱。深度特征的深度是制作特征所需的基元的數(shù)量。
我們可以將功能堆疊到我們想要的任何深度,但在實(shí)踐中,我從未用過超過2的深度。在此之后,生成的特征就很難解釋,但我鼓勵(lì)任何有興趣的人嘗試“更深入” 。
我們不必手動(dòng)指定特征基元,而是可以讓featuretools自動(dòng)為我們選擇特征。我們可以使用相同的ft.dfs函數(shù)調(diào)用,但不傳入任何特征基元:
# Perform deep feature synthesis without specifying primitives
features, feature_names = ft.dfs(entityset=es, target_entity='clients',
max_depth = 2)
features.head()
Featuretools為我們構(gòu)建了許多新特征。雖然此過程會(huì)自動(dòng)創(chuàng)建新特征,但仍需要數(shù)據(jù)科學(xué)家來弄清楚如何處理所有這些特征。例如,如果我們的目標(biāo)是預(yù)測客戶是否會(huì)償還貸款,我們可以尋找與指定結(jié)果最相關(guān)的特征。此外,如果我們有領(lǐng)域知識,我們可以使用它來選擇特定的特征基元或種子深度特征合成候選特征。
例如,MEAN(payments.payment_amount)列是深度為1的深層特征,因?yàn)樗鞘褂脝蝹€(gè)聚合創(chuàng)建的。深度為2的特征是LAST(貸款(MEAN(payments.payment_amount))這是通過堆疊兩個(gè)聚合來實(shí)現(xiàn)的:最后一個(gè)(最近的)在MEAN之上。這表示每個(gè)客戶最近貸款的平均支付額。
下一步
自動(dòng)化特征工程雖然解決了一個(gè)問題,但又導(dǎo)致了另一個(gè)問題:特征太多。雖然在擬合模型之前很難說哪些特征很重要,但很可能并非所有這些特征都與我們想要訓(xùn)練模型的任務(wù)相關(guān)。此外,特征太多可能會(huì)導(dǎo)致模型性能不佳,因?yàn)橐恍┎皇呛苡杏玫奶卣鲿?huì)淹沒那些更重要的特征。
特征過多的問題被稱為維度詛咒 。隨著特征數(shù)量的增加(數(shù)據(jù)的維度增加),模型越來越難以學(xué)習(xí)特征和目標(biāo)之間的映射。實(shí)際上,模型執(zhí)行所需的數(shù)據(jù)量隨著特征數(shù)量呈指數(shù)級增長。
維度詛咒與特征縮減(也稱為特征選擇)相對應(yīng):刪除不相關(guān)特征的過程。特征選擇可以采用多種形式:主成分分析(PCA),SelectKBest,使用模型中的特征重要性,或使用深度神經(jīng)網(wǎng)絡(luò)進(jìn)行自動(dòng)編碼。但是,減少功能是另一篇文章的另一個(gè)主題。目前,我們知道我們可以使用featuretools以最小的努力從許多表創(chuàng)建許多功能!
結(jié)論
與機(jī)器學(xué)習(xí)中的許多主題一樣,使用featuretools的自動(dòng)化特征工程是一個(gè)基于簡單想法的復(fù)雜概念。使用實(shí)體集,實(shí)體和關(guān)系的概念,featuretools可以執(zhí)行深度特征合成以新建特征。
聚合就是將深度特征合成依次將特征基元堆疊 ,利用了跨表之間的一對多關(guān)系,而轉(zhuǎn)換是應(yīng)用于單個(gè)表中的一個(gè)或多個(gè)列的函數(shù),從多個(gè)表構(gòu)建新特征。
在以后的文章中,我將展示如何使用這種技術(shù)解決現(xiàn)實(shí)中的問題,也就是目前正在Kaggle上主持的Home Credit Default Risk競賽。請繼續(xù)關(guān)注該帖子,同時(shí)閱讀此介紹以開始參加比賽!我希望您現(xiàn)在可以使用自動(dòng)化特征工程作為數(shù)據(jù)科學(xué)管道的輔助工具。模型的性能是由我們提供的數(shù)據(jù)所決定的,而自動(dòng)化功能工程可以幫助提高建立新特征的效率。
文章題目:如何用Python做自動(dòng)化特征工程
URL標(biāo)題:http://jinyejixie.com/article0/gpgcio.html
成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供服務(wù)器托管、微信小程序、外貿(mào)網(wǎng)站建設(shè)、定制網(wǎng)站、網(wǎng)頁設(shè)計(jì)公司、Google
聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請盡快告知,我們將會(huì)在第一時(shí)間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場,如需處理請聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時(shí)需注明來源: 創(chuàng)新互聯(lián)