我有一個非常大的大約45 GB的XML文件,我試圖解析並創建一個數據幀。 xml具有相當簡單的結構,如下所示。我想讀取標籤<event>
下的屬性,當型號爲輸入鏈接或左側鏈接。R當DOM和SAX解析器都失敗時該怎麼辦?
<?xml version="1.0" encoding="utf-8"?>
<events version="1.0">
<event time="10800.0" type="actend" person="9982471" link="21225" actType="home" />
<event time="10800.0" type="departure" person="9982471" link="21225" legMode="car" />
<event time="10800.0" type="PersonEntersVehicle" person="9982471" vehicle="9982471" />
<event time="10800.0" type="actend" person="9656271" link="21066" actType="home" />
<event time="10833.0" type="entered link" person="4250461" link="24329" vehicle="4250461" />
<event time="10835.0" type="left link" person="1662941" link="29242" vehicle="1662941" />
<event time="10835.0" type="entered link" person="1662941" link="29239" vehicle="1662941" />
<event time="10836.0" type="left link" person="7651702" link="7359" vehicle="7651702" />
<event time="10836.0" type="entered link" person="7651702" link="7407" vehicle="7651702" />
<event time="10840.0" type="left link" person="8909152" link="5664" vehicle="8909152" />
</events>
我試過基於DOM的xmlparse()
函數,但由於內存問題,它沒有幫助。然後,我嘗試了一個基於SAX的代碼(如下所示),但它耗時太長。例如,要讀取1%的樣本並從中創建一個數據框,我花了大約5個小時。因此,爲了完成整個數據,我需要大約20天的時間(假設它可以線性縮放)。你能幫我解決這個問題嗎?以下是指向very small sample,1% sample,5% sample和full data的鏈接。
這是我使用的SAX代碼。
library(XML)
branchFunction <- function() {
store <- new.env()
new_counter <- (function() {
i <- 0
function() {
i <<- i + 1
i
}
})()
func <- function(x, ...) {
ns <- getNodeSet(x,path = "//event[@type='left link' or @type='entered link']")
value <- lapply(ns, xmlAttrs)
store[[toString(new_counter())]] <- value
}
getStore <- function() { as.list(store) }
list(event = func, getStore=getStore)
}
myfunctions <- branchFunction()
xmlEventParse(file = "percent1.gz", handlers = NULL, branches = myfunctions)
l <- myfunctions$getStore()
l <- unlist(l, recursive = FALSE)
df <- data.frame(matrix(unlist(l), nrow=length(l), byrow=T),stringsAsFactors=FALSE)
colnames(df) <- c("time", "type", "person", "link", "carid")
的輸出必須是這樣的
> head(df)
time type person link carid
1 10934.0 entered link 9656271 16260 9656271
2 10935.0 left link 8909152 6014 8909152
3 10935.0 entered link 8909152 6034 8909152
4 10936.0 left link 1504062 25541 1504062
5 10936.0 entered link 1504062 25384 1504062
6 10936.0 left link 3055801 31464 3055801
你做錯事在你的SAX方法,可能重新處理每個XPath表達式整個文件。 –
它可能是。但是,我不知道我的代碼是否以及什麼是問題。 – Gandalf
在XPath中,雙向正斜槓'//'搜索xml文檔中的任何地方,並且通常被認爲是一種昂貴的方法,因爲每個命令都會掃描樹結構中的所有潛在後代。 – Parfait