向量特性與操作方式
我們在約維安計畫:建立基本資料單位「向量」暸解了如何建立不同類型的向量,包含有:數值向量(numeric
)、整數向量(integer
)、文字向量(character
)、邏輯向量(logical
)、日期向量(Date
)、日期時間向量(POSIXct POSIXt
)與未定義值向量(NA/NULL/NaN/-Inf/Inf
)。向量有許多的特性與操作方式值得我們留意及學習,包含有向量是單一類型的、向量可以判斷和轉換類型以及向量元素的讀取、更新和刪除等操作。
向量是單一類型的
向量只能被宣告為單一類型,舉例來說,如果我們使用 c()
函數將不同類型的向量合併,R 語言會依照向上轉型(Upcasting)規則,自動並且隱性地用其中一個更精確的類型去記錄合併後的向量類型。例如將邏輯向量與整數向量合併,會自動獲得整數向量的結果(因為邏輯 FALSE
與 TRUE
能夠分別用整數 0 與 1 包含);或者將整數向量與數值向量合併,會自動獲得數值向量的結果(因為整數能夠用浮點數包含)。
favorite_integers <- c(FALSE, TRUE, 7L, 24L, 25L)
favorite_numbers <- c(7L, 24.0, 25.0)
print(class(favorite_integers))
print(class(favorite_numbers))
向量可以判斷類型
R 語言針對向量類型的判斷除了使用 class()
與 typeof()
函數能夠直截了當地告訴我們答案以外,也能夠使用一系列 is.向量類型()
函數判斷輸入的向量是否為某個指定的向量類型。除了判斷日期向量與日期時間向量要使用的是 inherits()
函數,其他都可以使用 is.向量類型()
系列函數判斷。
is.numeric()
:判斷是否為數值向量。is.integer()
:判斷是否為整數向量。is.character()
:判斷是否為文字向量。is.logical()
:判斷是否為邏輯向量。inherits(x, what = "Date")
:判斷是否為日期向量。inherits(x, what = "POSIXct")
:判斷是否為日期時間向量。is.na()
:判斷是否為遺漏值向量。is.null()
:判斷是否為空值向量。is.nan()
:判斷是否為非數值向量。is.infinite()
:判斷是否為無限大數值向量。
# is.numeric()
print(is.numeric(7))
print(is.numeric("7"))
# is.integer()
print(is.integer(7L))
print(is.integer(7))
# is.character()
print(is.character("FALSE"))
print(is.character(FALSE))
# is.logical()
print(is.logical(FALSE))
print(is.logical("FALSE"))
# inherits()
sys_date <- Sys.Date()
sys_time <- Sys.time()
print(inherits(sys_date, what = "Date"))
print(inherits("1970-01-01", what = "Date"))
print(inherits(sys_time, what = "POSIXct"))
print(inherits("1970-01-01 00:00:00", what = "POSIXct"))
# is.na()
print(is.na(NA))
print(is.na("NA"))
# is.null()
print(is.null(NULL))
print(is.null("NULL"))
# is.nan()
print(is.nan(NaN))
print(is.nan("NaN"))
# is.infinite()
print(is.infinite(Inf))
print(is.infinite("Inf"))
向量可以轉換類型
R 語言針對向量類型的轉換夠使用一系列 as.向量類型()
函數轉換輸入的向量為某個指定的向量類型。
as.numeric()
:轉換為數值向量。as.integer()
:轉換為整數向量。as.character()
:轉換為文字向量。as.logical()
:轉換為邏輯向量。as.Date()
:轉換為日期向量。as.POSIXct()
:轉換為日期時間向量。as.na()
:轉換為遺漏值向量。as.null()
:轉換為空值向量。as.nan()
:轉換為非數值向量。as.infinite()
:轉換為無限大數值向量。
使用 as.numeric()
函數轉換輸入為數值向量,輸入整數向量、邏輯向量、日期向量或日期時間向量都能順利轉換。
# as.numeric()
print(as.numeric(7L))
print(as.numeric(FALSE))
print(as.numeric(TRUE))
print(as.numeric(sys_date))
print(as.numeric(sys_time))
使用 as.integer()
函數轉換輸入為整數向量,輸入沒有小數位數(或小數位數為零)的數值向量、邏輯值向量、日期向量或日期時間向量都能順利轉換。
# as.integer()
print(as.integer(7.00))
print(as.integer(FALSE))
print(as.integer(TRUE))
print(as.integer(sys_date))
print(as.integer(sys_time))
使用 as.logical()
函數轉換輸入為邏輯向量,輸入數值或整數類型的 0 會轉換成為 FALSE
,其他則一律轉換為 TRUE
。輸入文字向量的 "FALSE"
、"False"
或 "false"
會轉換為 FALSE
,反之輸入文字向量的 "TRUE"
、"True"
或 "true"
會轉換為 TRUE
。
# as.logical()
print(as.logical(0))
print(as.logical(0L))
print(as.logical(1))
print(as.logical(1L))
print(as.logical(sys_date))
print(as.logical(sys_time))
使用 as.character()
函數轉換輸入為文字向量,輸入任意向量類型都能順利轉換。
# as.character()
print(as.character(7))
print(as.character(7L))
print(as.character(FALSE))
print(as.character(TRUE))
print(as.character(sys_date))
print(as.character(sys_time))
使用 as.Date()
函數轉換輸入為日期向量,我們可以輸入文字向量讓 R 語言轉換成日期向量。
使用 as.POSIXct()
函數轉換輸入為日期時間向量,我們可以輸入文字向量讓 R 語言轉換成日期時間向量,如果沒有指定參數 tz
會預設使用電腦的時區。
R 語言預設可以識別 %Y-%m-%d %H:%M:%S
或 %Y/%m/%d %H:%M:%S
這兩種日期時間的文字格式,如果是其他格式,必須要加入 format
參數告知被記錄的日期時間格式為何,函數才能順利轉換。常用的文字對應日期、日期時間格式有:
%a
:縮寫的星期幾,從 Sun 至 Sat。%A
:全稱的星期幾,從 Sunday 至 Saturday。%b
:縮寫的月份,從 Jan 至 Dec。%B
:全稱的月份,從 January 至 December。%d
:月份中的第幾天,從 01 至 31。%m
:以兩位數字表示的月份,從 01 至 12。%Y
:以四位數字表示的西元年份,從 0 至 9999。%H
:以兩位數字表示的小時,從 00 至 23。%M
:以兩位數字表示的分鐘,從 00 至 59。%S
:以兩位數字表示的秒數,從 00 至 59。
# as.Date()
print(as.Date("1970-01-01"))
print(as.Date("1970/01/01"))
print(as.Date("01-01-1970", format = "%m-%d-%Y"))
print(as.Date("01/01/70", format = "%m/%d/%y"))
# as.POSIXct()
print(as.POSIXct("1970-01-01 00:00:00"))
print(as.POSIXct("01-01-1970 00:00:00", format = "%m-%d-%Y %H:%M:%S"))
print(as.POSIXct("1970-01-01 00:00:00", tz = "GMT"))
向量元素的讀取
對於長度超過 1 的向量我能夠使用三種技巧讀取其中的元素:
索引(Indexing)。
切割(Slicing)。
邏輯篩選(Logical filtering)。
向量像是有格子的抽屜,每個格子上面都有一個索引值,方便 R 語言搜尋放在裡頭的資料,這個索引值從左邊由 1 起始計算。
# Indexing
four_seasons <- c("spring", "summer", "autumn", "winter")
print(four_seasons[1])
print(four_seasons[2])
print(four_seasons[3])
print(four_seasons[4])
當索引值是以 start:stop
建立的數值間距為 1 數值向量時,這樣的技巧就稱為切割(Slicing),意即取出一個向量中的某片段。
# Slicing
print(four_seasons[1:3])
print(four_seasons[2:4])
切割也能用 c()
函數結合多個索引值傳入,也可以接受負的索引值,表示採用負面表列方式讀取其中的元素。
# Slicing
print(four_seasons[c(1, 3)])
print(four_seasons[c(2, 4)])
print(four_seasons[c(-2, -4)])
print(four_seasons[c(-1, -3)])
除了使用索引或切割的技巧,亦可以對向量應用條件敘述(Conditional statement),進而產生邏輯向量作為對原向量篩選的依據,會保留判斷為 TRUE
位置的元素。
# Logical filtering
favorite_season <- four_seasons == "winter"
print(favorite_season)
print(four_seasons[favorite_season])
向量元素的更新和刪除
透過索引(Indexing)與 <-
來更新和刪除向量中的元素。
# Update
four_seasons[3] <- "fall"
print(four_seasons)
# Delete
three_seasons <- four_seasons[-3]
print(three_seasons)
在初步暸解如何在 R 語言操作基本資料單位「向量」之後,約維安計畫:操作基本資料單位「向量」來到尾聲,希望您也和我一樣期待下一篇文章。
延伸閱讀
對於這篇文章有什麼想法呢?喜歡😻、留言🙋♂️或者分享🙌