如何在OSX上的Swift 6.1中解析XML字符串?

时间:2014-10-27 04:34:10

标签: xcode macos swift xcode6

我是Swift的新手,我正在尝试创建一个解析xml文件的OSX终端应用。我已经将文件读入字符串,但无法弄清楚如何将其解析为一个结构,然后我可以导航并从中提取数据。似乎NSXMLDocument似乎需要一个URL而NSXMLParser需要一个委托,但我最初的尝试无法让它们起作用。

这是我到目前为止所得到的:

import Foundation
import Cocoa

let path = "//Users/<path>/someFile.xml"

var err: NSError?
let content = String.stringWithContentsOfFile(path, encoding: NSUTF8StringEncoding, error: &err)

xml文件的结构如下:

<?xml version="1.0" encoding="UTF-8"?>
<Data>
  <Documents>
    <List>
      <Document name="name1" type="TYPE1" date="some string">
        <Items>
          <Item name="item1" dataType="DATATYPE1" version="1">
          <Item name="item2" dataType="DATATYPE9" version="4">
        </Items>
      </Document>
      <Document name="name2" type="TYPE4" date="some string">
      ...
    </List>
  </Documents>
</Data>

非常感谢您的帮助。

2 个答案:

答案 0 :(得分:2)

解析XML文档并不是那么简单,不能用代码中的单行代码完成。

要使用NSXMLParser解析它,您需要一个实现NSXMLParserDelegate协议的自定义类,如下所示:

class myXMLParser: NSObject, NSXMLParserDelegate {
    ...

    func parseFile(filename: String) {
        let url = NSBundle.mainBundle().URLForResource(filename, withExtension: "xml")

        if let parser = NSXMLParser(contentsOfURL: url) {
            parser.delegate = self
            parser.parse()
        }
    }   


    func parserDidStartDocument(parser: NSXMLParser!) {
        ...
    }

    func parserDidEndDocument(parser: NSXMLParser!) {
        ...
    }

    func parser(parser: NSXMLParser!, didStartElement elementName: String!, namespaceURI: String!, qualifiedName qName: String!, attributes attributeDict: [NSObject : AnyObject]!) {
        ...
    }

    func parser(parser: NSXMLParser!, foundCharacters string: String!) {
        ...
    }

    func parser(parser: NSXMLParser!, didEndElement elementName: String!, namespaceURI: String!, qualifiedName qName: String!) {
        ...
    }

}

因此,无论何时使用didStartElement检索新元素,都必须检查它是什么元素以及您期望进一步的子元素。这一切都取决于XML文档的结构,因此没有一个解决方案可以给你。

答案 1 :(得分:2)

NSXMLDocument用法如下:

let fm = NSFileManager.defaultManager()
var err : NSError?
let userDirectory = fm.URLForDirectory(.UserDirectory, inDomain: .UserDomainMask, appropriateForURL: nil, create: false, error: &err)
if err != nil {
  // ...
}

if let path = userDirectory?.URLByAppendingPathComponent("someFile.xml") {
  NSXMLDocument(contentsOfURL: configURL, options: 0, error: &err)
  if err != nil {
    // ...
  }

  if let rootNode = config?.rootElement() {
    // ...
  }
}