利用pandas進(jìn)行數(shù)據(jù)清洗的方法
我們有下面的一個(gè)數(shù)據(jù),利用其做簡(jiǎn)單的數(shù)據(jù)分析。
這是一家服裝店統(tǒng)計(jì)的會(huì)員數(shù)據(jù)。最上面的一行是列坐標(biāo),最左側(cè)一列是行坐標(biāo)。列坐標(biāo)中,第 0 列代表的是序號(hào),第 1 列代表的會(huì)員的姓名,第 2 列代表年齡,第 3 列代表體重,第 4~6 列代表男性會(huì)員的三圍尺寸,第 7~9 列代表女性會(huì)員的三圍尺寸。
數(shù)據(jù)清洗規(guī)則總結(jié)為以下 4 個(gè)關(guān)鍵點(diǎn),統(tǒng)一起來(lái)叫“完全合一”,下面來(lái)解釋下:
- 完整性:?jiǎn)螚l數(shù)據(jù)是否存在空值,統(tǒng)計(jì)的字段是否完善。
- 全面性:觀察某一列的全部數(shù)值,比如在 Excel 表中,我們選中一列,可以看到該列的平均值、最大值、最小值。我們可以通過(guò)常識(shí)來(lái)判斷該列是否有問(wèn)題,比如:數(shù)據(jù)定義、單位標(biāo)識(shí)、數(shù)值本身。
- 合法性:數(shù)據(jù)的類型、內(nèi)容、大小的合法性。比如數(shù)據(jù)中存在非 ASCII 字符,性別存在了未知,年齡超過(guò)了 150 歲等。
- 唯一性:數(shù)據(jù)是否存在重復(fù)記錄,因?yàn)閿?shù)據(jù)通常來(lái)自不同渠道的匯總,重復(fù)的情況是常見(jiàn)的。行數(shù)據(jù)、列數(shù)據(jù)都需要是唯一的,比如一個(gè)人不能重復(fù)記錄多次,且一個(gè)人的體重也不能在列指標(biāo)中重復(fù)記錄多次。
1、完整性
1.1 缺失值
一般情況下,由于數(shù)據(jù)量巨大,在采集數(shù)據(jù)的過(guò)程中,會(huì)出現(xiàn)有些數(shù)據(jù)單元沒(méi)有被采集到,也就是數(shù)據(jù)存在缺失。通常面對(duì)這種情況,我們可以采用以下三種方法:
- 刪除:刪除數(shù)據(jù)缺失的記錄
- 均值:使用當(dāng)前列的均值填充
- 高頻:使用當(dāng)前列出現(xiàn)頻率最高的數(shù)據(jù)
比如我們相對(duì)data[‘Age']中缺失的數(shù)值使用平均年齡進(jìn)行填充,可以寫(xiě):
df['Age'].fillna(df['Age'].mean(), inplace=True)
如果我們用最高頻的數(shù)據(jù)進(jìn)行填充,可以先通過(guò) value_counts 獲取 Age 字段最高頻次 age_maxf,然后再對(duì) Age 字段中缺失的數(shù)據(jù)用 age_maxf 進(jìn)行填充:
age_maxf = train_features['Age'].value_counts().index[0] train_features['Age'].fillna(age_maxf, inplace=True)
1.2 空行
我們發(fā)現(xiàn)數(shù)據(jù)中有一個(gè)空行,除了 index 之外,全部的值都是 NaN。Pandas 的 read_csv() 并沒(méi)有可選參數(shù)來(lái)忽略空行,這樣,我們就需要在數(shù)據(jù)被讀入之后再使用 dropna() 進(jìn)行處理,刪除空行。
# 刪除全空的行 df.dropna(how='all',inplace=True)
2、全面性
列數(shù)據(jù)的單位不統(tǒng)一
如果某一列數(shù)據(jù)其單位并不統(tǒng)一,比如weight列,有的單位為千克(Kgs),有的單位是磅(Lbs)。
這里我們使用千克作為統(tǒng)一的度量單位,將磅轉(zhuǎn)化為千克:
# 獲取 weight 數(shù)據(jù)列中單位為 lbs 的數(shù)據(jù) rows_with_lbs = df['weight'].str.contains('lbs').fillna(False) print df[rows_with_lbs] # 將 lbs轉(zhuǎn)換為 kgs, 2.2lbs=1kgs for i,lbs_row in df[rows_with_lbs].iterrows(): # 截取從頭開(kāi)始到倒數(shù)第三個(gè)字符之前,即去掉lbs。 weight = int(float(lbs_row['weight'][:-3])/2.2) df.at[i,'weight'] = '{}kgs'.format(weight)
3、合理性
非ASCII字符
假設(shè)在數(shù)據(jù)集中 Firstname 和 Lastname 有一些非 ASCII 的字符。我們可以采用刪除或者替換的方式來(lái)解決非 ASCII 問(wèn)題,這里我們使用刪除方法,也就是用replace方法:
# 刪除非 ASCII 字符 df['first_name'].replace({r'[^\x00-\x7F]+':''}, regex=True, inplace=True) df['last_name'].replace({r'[^\x00-\x7F]+':''}, regex=True, inplace=True)
4、唯一性
4.1 一列有多個(gè)參數(shù)
假設(shè)姓名(Name)包含了兩個(gè)參數(shù) Firstname和Lastname。為了達(dá)到數(shù)據(jù)整潔的目的,我們將 Name 列拆分成 Firstname 和 Lastname 兩個(gè)字段。我們使用 Python 的 split 方法,str.split(expand=True),將列表拆成新的列,再將原來(lái)的 Name 列刪除。
# 切分名字,刪除源數(shù)據(jù)列 df[['first_name','last_name']] = df['name'].str.split(expand=True) df.drop('name', axis=1, inplace=True)
4.2 重復(fù)數(shù)據(jù)
我們校驗(yàn)一下數(shù)據(jù)中是否存在重復(fù)記錄。如果存在重復(fù)記錄,就使用 Pandas 提供的 drop_duplicates() 來(lái)刪除重復(fù)數(shù)據(jù)。
# 刪除重復(fù)數(shù)據(jù)行 df.drop_duplicates(['first_name','last_name'],inplace=True)
這樣,我們就將上面案例中中的會(huì)員數(shù)據(jù)進(jìn)行了清理,來(lái)看看清理之后的數(shù)據(jù)結(jié)果。
到此這篇關(guān)于利用pandas進(jìn)行數(shù)據(jù)清洗的方法的文章就介紹到這了,更多相關(guān)pandas 數(shù)據(jù)清洗內(nèi)容請(qǐng)搜索本站以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持本站!
版權(quán)聲明:本站文章來(lái)源標(biāo)注為YINGSOO的內(nèi)容版權(quán)均為本站所有,歡迎引用、轉(zhuǎn)載,請(qǐng)保持原文完整并注明來(lái)源及原文鏈接。禁止復(fù)制或仿造本網(wǎng)站,禁止在非www.sddonglingsh.com所屬的服務(wù)器上建立鏡像,否則將依法追究法律責(zé)任。本站部分內(nèi)容來(lái)源于網(wǎng)友推薦、互聯(lián)網(wǎng)收集整理而來(lái),僅供學(xué)習(xí)參考,不代表本站立場(chǎng),如有內(nèi)容涉嫌侵權(quán),請(qǐng)聯(lián)系alex-e#qq.com處理。