解析XML数据
问题描述:
我的XML文件:解析XML数据
<?xml version="1.0"?>
<root>
<msg>
<MessageError>
<BookingID>123</BookingID>
<Error>Invalid patient name</Error>
<Error>PATIENT NOT FOUND</Error>
<Message>Incoming MESSAGE DATA 1</Message>
</MessageError>
<MessageError>
<BookingID>456</BookingID>
<Error>Undefined patient account number.</Error>
<Error>Undefined Account Number</Error>
<Message>Incoming MESSAGE DATA 2</Message>
</MessageError>
<MessageError>
<BookingID>789</BookingID>
<Error>DOB invalid</Error>
<Message>Incoming MESSAGE DATA 3</Message>
</MessageError>
</msg>
</root>
我的TCL脚本:
set dom [dom parse $msg]
set root [$dom documentElement]
set MessageError [$root selectNodes "/root/msg/MessageError" ]
foreach node $MessageError {
set Error [$root selectNodes {/root/msg/MessageError/Error} ]
#set bookingid [$MessageError text]
#echo "BookingIDXML - $bookingid"
#set message [$MessageError text]
#echo "MessageXML - $message"
foreach errornode $Error {
set error [$errornode text]
echo "ErrorXML - $error"
}
}
我的输出:
ErrorXML - Invalid patient name
ErrorXML - PATIENT NOT FOUND
ErrorXML - Undefined patient account number.
ErrorXML - Undefined Account Number
ErrorXML - DOB invalid
ErrorXML - Invalid patient name
ErrorXML - PATIENT NOT FOUND
ErrorXML - Undefined patient account number.
ErrorXML - Undefined Account Number
ErrorXML - DOB invalid
ErrorXML - Invalid patient name
ErrorXML - PATIENT NOT FOUND
ErrorXML - Undefined patient account number.
ErrorXML - Undefined Account Number
ErrorXML - DOB invalid
目前缺少文档中互联网与这个强大的工具。我如何获得输出?我的代码的注释“#”部分不起作用。
BookingIDXML - 123
ErrorXML - Invalid patient name
MessageXML - Incoming MESSAGE DATA 1
BookingIDXML - 123
ErrorXML - PATIENT NOT FOUND
MessageXML - Incoming MESSAGE DATA 1
BookingIDXML - 456
ErrorXML - Undefined patient account number.
MessageXML - Incoming MESSAGE DATA 2
BookingIDXML - 465
ErrorXML - Undefined Account Number
MessageXML - Incoming MESSAGE DATA 2
BookingIDXML - 789
ErrorXML - DOB invalid
MessageXML - Incoming MESSAGE DATA 3
在此先感谢。
答
selectNodes
方法使用XPath(其中非常好,记录为)找到要返回的结果,其中上下文节点是您调用该方法的对象。因此,要找到特定MessageError
的Error
节点,您必须从正确的角度出发。特别是,你可能需要的代码做这样的事情:
foreach messageError [$root selectNodes "/root/msg/MessageError"] {
# Print some general info (to separate error groups)
set bookingID [lindex [$messageError selectNodes "BookingID"] 0]
puts "ID: [$bookingID text]"
set message [lindex [$messageError selectNodes "Message"] 0]
puts "Message: [$message text]"
# Print the errors
foreach error [$messageError selectNodes "Error"] {
puts "Error: [$error text]"
}
}
如果你愿意,你可以使用./Error
代替Error
作为XPath的搜索词;效果会是一样的,但看起来更像是一条路。你不应该从文档的根目录开始搜索(因为/root/msg/MessageError/Error
会这样做),因为那样你会找到与该路径匹配的所有内容,而不仅仅是当前子上下文中的位。 (将子上下文看作有点像文件系统中的当前目录,并且元素有点像目录;这只是一个部分的比喻 - DOM树不是目录 - 但它仍然有点类似。)
答
你必须引用$errornode
DOM节点在你的代码,例如:
foreach errornode $Error {
set bookingid [[$errornode selectNodes "../BookingID"] text]
set error [$errornode text]
set message [[$errornode selectNodes "../Message"] text]
puts "BookingIDXML - $bookingid"
puts "ErrorXML - $error"
puts "MessageXML - $message"
puts ""
}
但要注意:当多个节点查询(例如$errornode selectNodes "../Message"
)匹配的selectNodes
方法将返回一个列表。如果是这种情况,您必须对每个列表元素使用text
方法。
非常感谢Donal。我是一个tDOM和XML解析的总新手。你的解释非常详细。我现在明白了,看到我的错误。它有点可怕,你的代码在第一时间工作。我将阅读XPath。 – alsnow 2013-04-26 13:03:48
@user我用过几次tDOM和XPath;该模式(使用'foreach'来查看所找到的节点列表)比手动查找DOM树容易得多。 (在所有使用DOM_的单一语言中也是这样,严重的是,如果你使用DOM,那么至少要学习XPath的基本部分,我很高兴我做到了!) – 2013-04-28 18:01:12