Re: [問題] read.table 多個sep 遺失值miss

看板R_Language作者 (天)時間9年前 (2016/05/01 02:16), 9年前編輯推噓1(100)
留言1則, 1人參與, 最新討論串2/2 (看更多)
※ 引述《f496328mm (為什麼會流淚)》之銘言: : 問題一 : 我要讀的是筆記本txt檔 : 檔案太大無法先用excel處理 : 我的分隔符號有多個 請問要怎麼寫?? : 我的code : read.table("d:\\xxx.txt" ,sep=";", fill=T, quote="") : 我想要用 ; 和 空格 當作分隔符號 未來可能再增加 假設你資料長這樣,可以先用regex把分隔符號抓出來,再用fread處理: sam 18; boy paul; 20 boy charlotte; 21; girl christy 17 girl 好讀版:http://pastebin.com/QjwNiyNK 備註很長,不想看就轉下一頁吧,無所謂的murmur XD (備註:library後面註解是該套件會用到的函數,我盡量減少使用奇怪的函數, %>>%部分,我這裡用法幾乎都跟%>%一樣,去看magrittr介紹即可, 有興趣了解更多,再到作者網站看,%>>%多了不少好用的功能, data.table主要是用fread,data.table跟setnames都可以分別用 data.frame, `names<-`這兩個函數取代,rlply可以用replicate取代 mutate也可以用base的transform取代,str_c跟paste一樣, str_replace_all只是把gsub原本放字串的位置移到第一個,方便pipe, 還有其他問題或是不會取代函數的話,再推文或是回文發問吧, 至於為什麼要用其他函數,其函數有其他好處加上習慣,甚至只是因為style問題, 就不在程式中做取代了) code: library(data.table) # fread, data.table, setnames library(pipeR) # %>>% library(plyr) # rlply library(dplyr) # mutate library(stringr) # str_replace_all, str_c readLines(textConnection('sam 18; boy paul; 20 boy charlotte; 21; girl christy 17 girl')) %>>% str_replace_all("([a-zA-Z0-9]);? ", "\\1,") %>>% # str_replace_all比gsub適合用在pipeR str_c(collapse = "\n") %>>% fread %>>% # str_c = paste setnames(c("name", "age", "sex")) %>>% mutate(age = as.integer(age)) # name age sex # 1 sam 18 boy # 2 paul 20 boy # 3 charlotte 21 girl # 4 christy 17 girl 用兩百萬個row測試看看: # data generation textData <- raply(5e5, 'sam 18; boy paul; 20 boy charlotte; 21; girl christy 17 girl') %>>% str_c(collapse = "\n") library(microbenchmark) # microbenchmark microbenchmark(test = textData %>>% str_replace_all("([a-zA-Z0-9]);? ", "\\1,") %>>% str_c(collapse = "\n") %>>% fread %>>% setnames(c("name", "age", "sex")) %>>% mutate(age = as.integer(age)), times = 10L) # Unit: seconds # expr min lq mean median uq max neval # test 4.489137 4.520529 4.528179 4.529275 4.543055 4.557189 10 平均一次4.5秒左右,全距也很小,所以兩百萬列不是問題 : ========================================================== : 問題二 : 我的資料中 有些地方沒有值 所以當初在存的時候就直接忽略 連空白都沒留 : 像這樣: : sam;16;boy; 2015:00:09:59 : green;18;gril : paul;20; 2015:00:09:59 : 第一行是name : 第二行是age : 第三行是性別 : 但是paul沒有記錄到 所以直接記錄到第四行的time : green的time也沒記錄到 : 想問有沒有什麼方法解決 我目前只想到比較笨的方法 : 給它特定範圍去判斷 像性別不是boy就是gril 出現其他就給他NA : 還有 : 這樣讀資料也會因為每列資料col都不一樣 有的時候會出現問題 : 是可以讀成文字再去慢慢拆開 不過有點笨就是了 : 最後想問如果讀資料量上百萬筆 : 還是用read.table嗎? : 有沒有比較好的函數專門處理large data? : 謝謝 一樣用regex處理即可,速度也是相當快: pattern <- str_c("([a-z]*);?\\s*", "(\\d*)?;?\\s*", "(boy|girl)?;?\\s*", "(\\d{4}:\\d{2}:\\d{2}:\\d{2})?") # 第一個是第一欄位,第二個是第二欄位,依此類推 readLines(textConnection('sam;16;boy; 2015:00:09:59 green;18;girl; paul;20; 2015:00:09:59 charlotte; 21;')) %>>% str_replace_all(pattern, "\\1, \\2, \\3, \\4") %>>% str_replace_all(", , , ", "") %>>% str_c(collapse = "\n") %>>% fread(na.string="") %>>% setnames(c("name", "age", "sex", "time")) %>>% mutate(age = as.integer(age)) # name age sex time # 1 sam 16 boy 2015:00:09:59 # 2 green 18 girl <NA> # 3 paul 20 <NA> 2015:00:09:59 # 4 charlotte 21 <NA> <NA> # 這裡要為什麼要取代", , , ",我暫時想不出來為什麼 # 這裡不知道為什麼經過regex後,每一列會多出三個逗號,讓我匪夷所思QQ # 用兩百萬個row測試看看: # data generation textData <- raply(5e5, 'sam;16;boy; 2015:00:09:59 green;18;girl; paul;20; 2015:00:09:59 charlotte; 21;') %>>% str_c(collapse = "\n") library(microbenchmark) microbenchmark(test = readLines(textConnection(textData)) %>>% str_replace_all(pattern, "\\1, \\2, \\3, \\4") %>>% str_replace_all(", , , ", "") %>>% str_c(collapse = "\n") %>>% fread(na.string="") %>>% setnames(c("name", "age", "sex", "time")) %>>% mutate(age = as.integer(age)), times = 10L) # Unit: seconds # expr min lq mean median uq max neval # test 10.93214 10.9493 10.9683 10.96072 10.98294 11.04314 10 平均一次11秒左右,全距也很小,所以兩百萬列不是問題 最後murmur,這個資料真的長得很醜,我花了一小時才把這篇打完 還在測試不用regular expression的方法,能多快 發現讀一次檔案還是要80秒,實在太慢,最後就不PO上來了 這裡推薦一個網站學regex: http://regexone.com/ 題外話:這一篇文章值 185 Ptt幣 XDD -- R資料整理套件系列文: magrittr #1LhSWhpH (R_Language) http://tinyurl.com/j3ql84c data.table #1LhW7Tvj (R_Language) http://tinyurl.com/hr77hrn dplyr(上) #1LhpJCfB (R_Language) http://tinyurl.com/jtg4hau dplyr(下) #1Lhw8b-s (R_Language) tidyr #1Liqls1R (R_Language) http://tinyurl.com/jq3o2g3 -- ※ 發信站: 批踢踢實業坊(ptt.cc), 來自: 180.218.152.118 ※ 文章網址: https://www.ptt.cc/bbs/R_Language/M.1462040172.A.2C0.html ※ 編輯: celestialgod (180.218.152.118), 05/01/2016 02:34:01

05/01 10:58, , 1F
感謝!這應該算是高階寫法吧,又學到新東西啦
05/01 10:58, 1F
文章代碼(AID): #1N9FPiB0 (R_Language)
文章代碼(AID): #1N9FPiB0 (R_Language)