网上很多XML2JSON的算法中都习惯用一个“@attributes”把属性统一起来,一开始弄不明白为什么要这样,好像显得很多余,今天自己实现感受了下,明白是因为需要把自身属性的nodeName与子元素的属性区分开来,比如下面测试用例中的Title
在SO我也提问了下,有个大神详细解答了,比我的答案更贴切:
var xml2json = function (xml) {
if(xml.nodeType === 9){
xml = xml.children[0]
}
var obj = {}
if(xml.nodeType === 1){
if(xml.attributes.length > 0){
var attrs = xml.attributes,attrLen = attrs.length
for(var i = 0 ; i < attrLen ; i++){
var node = attrs[i]
obj[node.nodeName] = node.nodeValue
}
}
}
if(xml.children){
var children = xml.children
var childLen = children.length
for(var j = 0 ; j < childLen ; j++){
var curChild = children[j]
if(!obj[curChild.nodeName]){
//console.log(JSON.stringify(xml2json(curChild)))
console.log(curChild)
obj[curChild.nodeName] = xml2json(curChild)
}else {
if(!Array.isArray(obj[curChild.nodeName])){
var old = obj[curChild.nodeName]
var handler = obj[curChild.nodeName] = []
handler.push(old)
}
obj[curChild.nodeName].push(xml2json(curChild))
}
}
}
return obj
}
var xmlStr = '<ALEXA VER="0.9" URL="davidwalsh.name/" HOME="0" AID="=">'
+'<SD TITLE="A" FLAGS="" HOST="davidwalsh.name">'
+'<TITLE TEXT="David Walsh Blog :: PHP,MysqL,CSS,Javascript,MooTools,and Everything Else"/>'
+'<LINKSIN NUM="1102"/>'
+'<SPEED TEXT="1421" PCT="51"/>'
+''
+''
+'<POPULARITY URL="davidwalsh.name/" TEXT="7131"/>'
+'<REACH RANK="5952"/>'
+'<RANK DELTA="-1648"/>'
+' '
+''
var domparser = new DOMParser()
var xmlObj =domparser.parseFromString(xmlStr,'application/xml')
var jsonObj = xml2json(xmlObj)
console.log(jsonObj)
console.log(JSON.stringify(jsonObj))