iT邦幫忙

2023 iThome 鐵人賽

DAY 12
0
AI & Data

用R語言玩轉文字探勘系列 第 12

[Day 12] R語言中的文件資料結構

  • 分享至 

  • xImage
  •  

文件資料結構

文件資料結構介紹

這個章節會相對抽象一些。若你只是單純處理「文字資料」,例如選舉資料中的候選人欄位用 character 儲存,就比較不會遇上這個章節遇到的問題。

相反地,若你平常要和文件、語料打交道,那就可能遇到相關情境,例如A單位2022年/2023年的電子書、B單位2021年的電子書等,除了書本以外,還有很多元資料(metadata),就會遇到這個章節標題所說的「文件資料格式」,其實用其他詞可能比文件還精準,但為方便理解還是使用這個詞。

不過,為什麼需要資料框以外的文件資料結構?

使用資料框儲存文件資料確實很方便,因為資料框裡面其他欄位可以方便我們清理資料,例如前面展示過的篩選特定年份、利用stringr取代特定文字等,全部都能和dplyr配合進行。然而,在特定情境中,使用專為文件分析設計的資料結構會更為高效和方便,相關考慮因素有記憶體效率、計算效率、針對特定資料結構開發出的功能性、資料本身維度就比較高等。

文件資料格式種類

資料框

前面我們介紹tidytext的時候,就有看到利用資料框(dtaframe)儲存文件資料。再簡單介紹一次,利用資料框儲存文件資料,等同服膺tidy原則,每個列(row)都是一筆資料、一個觀測值(observation),每個行都是一個欄位、一個變數(variable),無論是Excel或者Google Spreadsheet,都是常見的資料框。

因為tidytext也是在tidyverse底下運行,所以都會用資料框方式儲存文件資料。

語料

語料(corpus),或稱文集,是一種在老派資料探勘專用套件tm(text mining簡稱)常見的資料結構。它具備數個特點,包含擴充性高,它可以儲存大規模文件;還有預處理方便,因為有許多內建專門針對語料資料結構的函數,例如大寫轉小寫、去除停用詞、提取詞幹等,不過這點後來其他套件也都做到了;有元數據(metadata)專用儲存結構,例如可以放上作者、出版社(書或者報章雜誌)、出版日期等。

雖然老派,但它還有在更新,你可以造訪tm官網獲得更多資訊。我沒有很習慣使用它,因為像是stringr或者quanteda都有更現代且更加彈性的函數,可以完成相同任務。

library(tm)
texts <- c("I love R.", "R is a language.", "Text mining with R.")
corpus <- Corpus(VectorSource(texts))
corpus <- tm_map(corpus, content_transformer(tolower))
corpus <- tm_map(corpus, removePunctuation)
corpus <- tm_map(corpus, removeNumbers)
corpus <- tm_map(corpus, removeWords, stopwords("en"))
inspect(corpus)

## <<SimpleCorpus>>
## Metadata:  corpus specific: 1, document level (indexed): 0
## Content:  documents: 3
## 
## [1]  love r        r   language   text mining  r

DTM與DFM

DTM和DFM概念相似,因此一併介紹。前者全名為文件詞彙矩陣(document term matrix),後者則是文件特徵矩陣(document feature matrix),差別只有 term 和 feature,其實非常相似,term 是指單一詞彙,feature
則是延伸概念,因為開發者認為應該從單一詞彙不夠彈性,所以用特徵或者變數的概念取代詞彙,這個特徵可能是單一詞彙,也可能不是,所以它的概念更上一層。

DTM的每一列代表詞彙、每一行代表文件、每一個值則是詞彙出現頻率(term frequencies),它同樣是tm中常用的資料結構。DTM則是quanteda的標準配備,每一列代表不限於詞彙的特徵、每一行代表文件、每一個值則可以是不同類型的數字。

library(tm)
texts <- c("I love R.", "R is a language.", "Text mining with R.")
corpus <- Corpus(VectorSource(texts))
dtm <- DocumentTermMatrix(corpus)
inspect(dtm) 

## <<DocumentTermMatrix (documents: 3, terms: 5)>>
## Non-/sparse entries: 5/10
## Sparsity           : 67%
## Maximal term length: 9
## Weighting          : term frequency (tf)
## Sample             :
##     Terms
## Docs language. love mining text with
##    1         0    1      0    0    0
##    2         1    0      0    0    0
##    3         0    0      1    1    1

library(quanteda)
texts <- c("我是R語言愛好者", "你喜歡R語言嗎?", "文字探勘有專門的R語言套件")
tokens <- tokens(texts)
dfm <- dfm(tokens)
dfm

## Document-feature matrix of: 3 documents, 15 features (57.78% sparse) and 0 docvars.
##        features
## docs    我是 r 語言 愛好者 你 喜歡 嗎 ? 文字 探勘
##   text1    1 1    1      1  0    0  0  0    0    0
##   text2    0 1    1      0  1    1  1  1    0    0
##   text3    0 1    1      0  0    0  0  0    1    1
## [ reached max_nfeat ... 5 more features ]

前面我們談到記憶體效率。當我們有數百萬篇文章需要分析時,使用矩陣儲存資料會更有效率,因為它們採用稀疏矩陣(sparse matrix)結構儲存,只儲存非零元素,從而節省記憶體。什麼意思呢?你可以想像,整理不同篇文章,彼此會有有一些共通出現的詞彙,例如「你」、「我」、「的」、「是」、「和」,但也會有些因文章主題而異的詞彙,例如政治類文章就會有「政黨」和「選舉」、娛樂類文章則會有「音樂」和「表演」。

在此情況下,我們用前面提到的DTM和DFM儲存文章資料,每個文件、每篇文章中,也就是每個列大部分的詞彙出現次數都是0。為什麼?AA文章可能用了250個詞彙、B文章則用了300個詞彙,它們共用的詞彙假設是50個,則我們可以想像,當文章數上升,這個矩陣就會頻繁加上新詞彙,因為共同出現的詞彙就是那些。

當某個矩陣中出現大多數值為0的狀況時,就可以使用專門用來儲存這種資料的稀疏矩陣,它只儲存非零值,以及這些非零值在矩陣中的位置,反正其他都是0。這樣便能大幅減少所需儲存空間,因此增加記憶體儲存效率。

不只是儲存而已,計算效率也能提升。你鐵定在數學課學過矩陣運算,像是線性代數課程就有很多介紹,所以處理矩陣時,既能用項量化運算加速,這會比資料框針對一個一個欄位慢慢處理還快。另外,矩陣也有專門開發的計算方式,例如奇異值分解(SVD),這些都是計算效率上升的展現。

另外,矩陣有專門設計的方法和函數,像是tmquanteda都有開發主題模型與情感分析的專用方法;DTM和DFM也支援高維度文本數據,如果是在資料框裡面,我們就可能要利用unnest或者其他方式處理,相對沒那麼直觀。這些就是使用資料框以外資料結構的解釋囉!


上一篇
[Day 11] 以R語言分詞 - 在R語言中使用ckip
下一篇
[Day 13] 文字探勘之前要先準備語料
系列文
用R語言玩轉文字探勘30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言