STATA 小技巧 (3):檢查重複值與遺失值
4 min readSep 4, 2021
當我們在清理資料時,很常需要去檢查重複值與遺失值。這一節會介紹相關的指令。
重複值
有時候我們有明確的背景知識,知道資料應該以哪個(組)變數為 identifier。這時可以透過 duplicates
系列的指令去檢查或排除不合理的重 複值。我以 Fig 3-6為例,條列說明 duplicates
系列的指令:
duplicates tag <varlist>, gen(<var>)
,對於<varlist>
值重複的樣本點,利用<var>
標記重複次數(沒重複時為 0),即 Fig 3–6 中的變數dup
。這個指令是我duplicates
系列中最常用的指令,通常會在使用後,利用br if <var> > 0
來查看為何會有重複值,並且判斷應該如何處 理。duplicates report <varlist>
會回報<varlist>
重複的情形。Fig 3-6 左下角展示了回報結果copy
:重複 2 次的樣本點總共 4 筆,也就是有 2 筆多餘;重複 3 次的樣本點總共 3 筆,也就是有 2 筆多餘。duplicates drop <varlist>, force
,對於<varlist>
值重複的樣本點,只留下「第一筆」 觀察到的樣本點。duplicates drop
如果沒放入任何<varlist>
的話,相當於對所有變數檢查是否重複。
當發現重複值之後,最實際的問題當然是我們該如何處理?以下是幾種可能的應對方式:
- 整筆丟掉:想像你有交易記錄的資料,你預期個人 id 與交易 id 應該是 identifier,但你卻發現重複值(也許是因為交易取消、退貨等原因), 這種情形自然是丟掉那些不應存在的樣本點。然而我們丟樣本時還是要謹慎:留意丟了多少比例、捨棄的原因等等。
- 只保留一筆:想像你在使用社會保險資料(如:Fig 3-6)並預期
id month
為 identifier。你發現了重複值,但這次的原因也許是因為同個人身兼了數份工作。這時我們也許希望從該月中挑選一筆具代表性的資料,這也許是投保薪資最高的那筆(較可能是正職)。這種情形,我個人習慣的方式是利用bys:
先將目標(薪資最高)的樣本點 sort 到組別頭或尾,再保留每組的頭或尾。指令大概像是:bys id year (wage): keep if _n == _N
。 - 彙整:接續社會保險資料的例子,也許資料本來就該先經過彙整,這時後不如就參考 3–2 的
collapse
或 2–4 的by:
,將資料彙整至id month
的 level 上。其實,前面提的保留最高薪資也是一種彙整方式(像是透過egen <v2>=max(v1)
)。
遺失值
我在 2–2 已經提到了 missing 值在邏輯運算中如何被操作,這邊會再做一些整理,並且舉例 missing 在指令中的影響:
- 數值與字串變數的 missing 分別為
.
、””
,當然有些時候其他值意義上也是 missing 像是0
或是” ”
,因此我們需要細心地檢查資料,比如說透過tab
、sum
或繪圖來觀察變數的分佈或敘述統計,並適時調整(例如:將體重的 0 改成 missing)。 - Missing 在數值變數的邏輯運算上被視為無限大。有趣的是,
egen
底下的許多函式都會排除 missing,也就是說,不必去的擔心egen max()
會因為一筆 missing 而回傳 missing。回頭看 2–2 介紹的條件統計量的計算,其實正是把不合條件的值轉變成 missing 並藉此排除。 if
條件示可以輕易地幫我們挑出 missing。如果不喜歡用一長串的<logic_exp>
表示的話,也可以試試看br if missing(v1, v2, v3…)
,只要v1
、v2
、v3
任一變數有 missing 就會被挑出來。
面對 missing,最簡單也是最常處理的方式就是逐列刪除,即完全捨去該樣本點。 然而,這麼做的風險就是忽略 missing 本身可能隱含的資訊,尤其當missing 不是隨機產生的。因此,有些時候我們可能會補值或是將變數類別化並納入 missing 類別。¹
[1]: 可以嘗試取平均或線性插值 ipolate
。當然,也可以嘗試利用其他變數建立模型預測。