C 語言的 XML 解析庫通常使用 libxml2 庫來處理 XML 文檔。雖然 libxml2 不支持直接將 XML 轉(zhuǎn)換成 JSON,但該庫提供了一些函數(shù)和數(shù)據(jù)結(jié)構(gòu),可以方便地實(shí)現(xiàn) XML 到 JSON 的轉(zhuǎn)換。下面給出一個(gè)例子,說明如何將 XML 轉(zhuǎn)換為 JSON 對(duì)象。 首先我們需要?jiǎng)?chuàng)建一個(gè)解析器,并使用 libxml2 庫中的函數(shù)將 XML 讀取進(jìn)來。以下代碼展示了如何解析 XML 文檔:
xmlDocPtr doc = xmlParseFile("example.xml"); if (doc == NULL) { printf("Failed to parse XML document."); return -1; } xmlNodePtr root = xmlDocGetRootElement(doc);上述代碼使用 xmlParseFile 函數(shù)從指定的 XML 文件中讀取數(shù)據(jù),并返回一個(gè)指向 xmlDoc 結(jié)構(gòu)體的指針。如果解析失敗,則會(huì)返回 NULL。接下來,我們使用 xmlDocGetRootElement 函數(shù)獲取文檔的根節(jié)點(diǎn)。 接著我們需要編寫一個(gè)函數(shù),將 XML 節(jié)點(diǎn)轉(zhuǎn)換為 JSON 對(duì)象。以下是一個(gè)示例函數(shù):
json_t* xmlToJson(xmlNodePtr node) { json_t* json = json_object(); xmlAttrPtr prop = node->properties; while (prop != NULL) { xmlChar* value = xmlNodeListGetString(node->doc, prop->children, 1); json_object_set_new(json, (char*)prop->name, json_string((char*)value)); xmlFree(value); prop = prop->next; } xmlNodePtr child = node->xmlChildrenNode; while (child != NULL) { if (child->type == XML_ELEMENT_NODE) { char* name = (char*)child->name; json_t* childJson = xmlToJson(child); json_object_set_new(json, name, childJson); } child = child->next; } return json; }上述代碼使用 json_object 函數(shù)創(chuàng)建一個(gè)新的 JSON 對(duì)象。然后遍歷 XML 節(jié)點(diǎn)的屬性列表,將每個(gè)屬性作為一個(gè)鍵值對(duì)添加到 JSON 對(duì)象中。接著遍歷 XML 節(jié)點(diǎn)的子節(jié)點(diǎn),如果是元素節(jié)點(diǎn),則遞歸調(diào)用 xmlToJson 函數(shù),并將返回值添加到當(dāng)前 JSON 對(duì)象中。 最后我們只需要將根節(jié)點(diǎn)傳入 xmlToJson 函數(shù),就可以得到一個(gè) JSON 對(duì)象,該對(duì)象與原始 XML 結(jié)構(gòu)相同。 下面是一個(gè)使用該函數(shù)的例子:
json_t* json = xmlToJson(root); char* output = json_dumps(json, JSON_INDENT(2)); printf("%s\n", output); free(output); json_decref(json);上述代碼將根節(jié)點(diǎn)傳入 xmlToJson 函數(shù),并使用 json_dumps 函數(shù)將 JSON 對(duì)象轉(zhuǎn)換為字符串輸出。最后需要釋放 JSON 對(duì)象和字符串的內(nèi)存。運(yùn)行該程序,輸出的 JSON 字符串與原始 XML 結(jié)構(gòu)相同,但鍵值對(duì)的順序可能會(huì)發(fā)生改變。