接下來我們要介紹如何從 Squid
這個 data frame 中萃取部分的資料出來,這個資料篩選的方式可以適用於任何的 data frame。
假設我們想要篩選出所有性別欄位(Sex
)是男性或女性的資料,首先我們先看一下 Sex
裡面的資料:
Squid$Sex
資料大概是這個樣子:
[1] 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 [20] 2 2 2 2 1 2 2 2 2 2 2 2 2 2 2 2 2 2 2 [39] 2 2 2 2 2 2 2 2 2 1 2 2 2 2 2 2 2 2 2 [略]
由於資料筆數很多,很難看出到底有哪一些值,我們可以用 unique
來將重複的數值去掉:
unique(Squid$Sex)
輸出為
[1] 2 1
這裡的 1
代表男性,而 2
代表女性,若要篩選出男性的資料,可以執行:
Sel <- Squid$Sex == 1 SquidM <- Squid[Sel, ] SquidM
輸出為
Sample Year Month Location Sex GSI 24 24 1 5 1 1 5.2970 48 48 1 5 3 1 4.2968 58 58 1 6 1 1 3.5008 60 60 1 6 1 1 3.2487 61 61 1 6 1 1 3.2304 [略]
這裡的第一行 Squid$Sex == 1
會檢查 Sex
的每一個值是否為 1
,產生一個跟 Sex
一樣長度的向量,若 Sex
對應的值為 1
,則產生 TRUE
,若 Sex
的值不是 1
,則產生 FALSE
,而這樣的向量稱為布林向量(boolean vector),在篩選資料時通常都會透過這樣的方式來指定子集合,因此我們將這個向量名為 Sel
。
第二行的 Squid[Sel, ]
是選擇所有 Sel
的值為 TRUE
的資料,並將這些資料儲存在 SquidM
中。
我們也可以將第一行與第二行合併,寫成:
SquidM <- Squid[Squid$Sex == 1, ] SquidM
若要篩選出女性的資料,可以執行:
SquidF <- Squid[Squid$Sex == 2, ] SquidF
這種透過布林向量篩選資料的方法可以用在非常多的地方,我們接下來想要根據 Location
這個欄位來篩選資料,首先看一下 unique
的結果:
unique(Squid$Location)
輸出為
[1] 1 3 4 2
如果我們想要篩選出 Location
是 1
、2
或 3
的資料,可以有以下幾種方式:
Squid123 <- Squid[Squid$Location == 1 | Squid$Location == 2 | Squid$Location == 3, ] Squid123 <- Squid[Squid$Location != 4, ] Squid123 <- Squid[Squid$Location < 4, ] Squid123 <- Squid[Squid$Location <= 3, ] Squid123 <- Squid[Squid$Location >= 1 & Squid$Location <= 3, ]
第一行是利用 OR 運算子(|
),將三個 ==
的判斷結果結合起來,而第二行是直接判斷 Location
是否不等於(!=
)4
,第三行與第四行則是使用「小於」(<
)以及「小於或等於」(<=
)來判斷,最後一行則是將兩個判斷結果用 AND 運算子(&
)結合,在這個例子中不管用哪一種寫法都可以獲得同樣的結果。
我們也可以同時使用多個欄位來產生布林向量,例如選擇 Sex
為 1
而且 Location
為 1
的資料:
SquidM.1 <- Squid[Squid$Sex == 1 & Squid$Location == 1,]
選擇 Sex
為 1
而且 Location
為 1
或 2
的資料:
SquidM.12 <- Squid[Squid$Sex == 1 & (Squid$Location == 1 | Squid$Location == 2), ]
有些初學者在產生布林向量時,很容易犯下這樣的錯誤:
SquidM <- Squid[Squid$Sex == 1, ] SquidM1 <- SquidM[Squid$Location == 1, ] SquidM1
輸出會像這樣:
Sample Year Month Location Sex 24 24 1 5 1 1 58 58 1 6 1 1 [略] NA NA NA NA NA NA NA.1 NA NA NA NA NA NA.2 NA NA NA NA NA [略]
這裡的第一行篩選出所有男性的資料,並儲存至 SquidM
,因此 SquidM
的資料筆數會小於原來 Squid
的資料筆數(假設 Squid
中有女性的資料),因此在第二行中 Squid$Location==1
的長度會比 SquidM
的資料筆數還要多,多出來的部分就會以 NA
遞補,因此產生這樣奇怪的結果。若要修正這個錯誤,應該要改成這樣:
SquidM <- Squid[Squid$Sex == 1, ] SquidM1 <- SquidM[SquidM$Location == 1, ] SquidM1
另外如果沒有任何資料符合篩選的條件,狀況會類似這樣:
Squid[Squid$Location == 1 & Squid$Year == 4 & Squid$Month == 1, ]
輸出為
[1] Sample Year Month Location [5] Sex GSI (or 0-length row.names)