iOS开发之XML简介及XML数据解析

XML即可扩展标记语言(eXtensible Markup Language)。标记是指计算机所能理解的信息符号,通过此种标记,计算机之间可以处理包含各种信息的文章等。如何定义这些标记,既可以选择国际通用的标记语言,比如HTML,也可以使用象XML这样由相关人士自由决定的标记语言,这就是语言的可扩展性。XML是从SGML中简化修改出来的。它主要用到的有XML、XSL和XPath等。

上面这段是对XML的一个基本定义,一个被广泛接受的说明。简单说,XML就是一种数据的描述语言,虽然它是语言,但是通常情况下,它并不具备常见语言的基本功能——被计算机识别并运行。只有依靠另一种语言,来解释它,使它达到你想要的效果或被计算机所接受。

记住以下几点就行了:

  • XML是一种标记语言,很类似HTML
  • XML的设计宗旨是传输数据,而非显示数据
  • XML标签没有被预定义。您需要自行定义标签。
  • XML被设计为具有自我描述性。
  • XML是W3C的推荐标准

总结:

XML是独立于软件和硬件的信息传输工具。 目前,XML在Web中起到的作用不会亚于一直作为 Web 基石的 HTML。 XML无所不在。XML是各种应用程序之间进行数据传输的最常用的工具,并且在信息存储和描述领域变得越来越流行。

1.1 XML属性

1.1.1 XML与HTML的主要差异

  • XML不是HTML的替代。
  • XML和HTML为不同的目的而设计。
  • XML被设计为传输和存储数据,其焦点是数据的内容。
  • HTML被设计用来显示数据,其焦点是数据的外观。
  • HTML旨在显示信息,而 XML 旨在传输信息

1.1.2 XML是不作为的。

也许这有点难以理解,但是XML不会做任何事情。XML被设计用来结构化、存储以及传输信息

1.1.3 XML仅仅是纯文本

XML没什么特别的。它仅仅是纯文本而已。有能力处理纯文本的软件都可以处理XML。 不过,能够读懂 XML 的应用程序可以有针对性地处理 XML 的标签。标签的功能性意义依赖于应用程序的特性。

1.1.4 XML允许自定义标签

上例中的标签没有在任何XML标准中定义过(比如和)。这些标签是由文档的创作者发明的。这是因为XML没有预定义的标签。

在HTML中使用的标签(以及HTML的结构)是预定义的。HTML文档只使用在HTML标准中定义过的标签(比如<p><h1> 等等)。

XML允许创作者定义自己的标签和自己的文档结构。

1.1.5 XML不是对HTML的替代

XML是对HTML的补充。

XML不会替代HTML,理解这一点很重要。在大多数 web 应用程序中,XML用于传输数据,而HTML用于格式化并显示数据。

1.2 XML的语法

XML的语法规则很简单,且很有逻辑。这些规则很容易学习,也很容易使用。

1.2.1 所有元素都必须有关闭标签

在XML中,省略关闭标签是非法的。所有元素都必须有关闭标签。 在HTML,经常会看到没有关闭标签的元素:

1
2
< p >This is a paragraph
< p >This is another paragraph

在XML中,省略关闭标签是非法的。所有元素都必须有关闭标签:

1
2
<p>This is a paragraph</p>
<p>This is another paragraph</p>

注释:您也许已经注意到XML声明没有关闭标签。这不是错误。声明不属于XML本身的组成部分。它不是XML元素,也不需要关闭标签。

1.2.2 XML标签对大小写敏感

XML元素使用XML标签进行定义。

XML标签对大小写敏感。在XML中,标签与标签是不同的。

必须使用相同的大小写来编写打开标签和关闭标签:

1
2
< Message >这是错误的。</ message >
< message >这是正确的。</ message >
1.2.3 XML标签对大小写敏感

在 HTML 中,常会看到没有正确嵌套的元素:

1
< b >< i >This text is bold and italic</ b ></ i >

在 XML中,所有元素都必须彼此正确地嵌套:

1
< b >< i >This text is bold and italic</ i ></ b >

在上例中,正确嵌套的意思是:由于<i>元素是在<b>元素内打开的,那么它必须在<b>元素内关闭。

1.2.4 XML文档必须有根元素

XML文档必须有一个元素是所有其他元素的父元素。该元素称为根元素。

1
2
3
4
5
< root >
   < child >
     < subchild >.....</ subchild >
   </ child >
</ root >
1.2.5 XML的属性值须加引号

与 HTML 类似,XML 也可拥有属性(名称/值的对)。 在 XML 中,XML 的属性值须加引号。请研究下面的两个 XML 文档。第一个是错误的,第二个是正确的:

1
2
3
4
5
6
7
8
9
< note date = 08 /08/2008>
< to >George</ to >
< from >John</ from >
</ note >
 
< note date = "08/08/2008" >
< to >George</ to >
< from >John</ from >
</ note >
1.2.6 实体引用

在 XML 中,一些字符拥有特殊的意义。 如果你把字符 “<” 放在 XML 元素中,会发生错误,这是因为解析器会把它当作新元素的开始。 这样会产生 XML 错误:

1
< message >if salary < 1000 then</message>

为了避免这个错误,请用实体引用来代替 “<” 字符:

1
< message >if salary &lt; 1000 then</ message >

在 XML 中,有 5 个预定义的实体引用:

1
2
3
4
5
&lt;    <   小于
&gt;    >   大于
&amp;   &   和号
'  '   单引号
&quot;  "   引号

注释:在 XML 中,只有字符 “<” 和 “&” 确实是非法的。大于号是合法的,但是用实体引用来代替它是一个好习惯。

1.2.7 XML中的注释

在 XML 中编写注释的语法与 HTML 的语法很相似:

1
<!-- This is a comment -->

在 XML 中,空格会被保留 HTML 会把多个连续的空格字符裁减(合并)为一个:

1
HTML:   Hello           my name is David.

输出: Hello my name is David. 在 XML 中,文档中的空格不会被删节。


2,XML的解析

1.初始化解析器,传入你要解析的数据。

2.parse,启动解析,返回一个是否解析成功Bool值。

3.基本你要处理的就在下面实现的1-5个代理方法了。

其实代理方法和详细,就是一个事物进行流程:

step1是准备解析,然后没意外就是执行到了——>

step2读取到第一个头节点了,然后如果内部有属性值,你可以获取出来,读完头节点,我们会进去值域——》

step3对于简单的节点,可能直接就是一个string值了,但是看例子我们会知道,很多情况下,该节点的值域包含的于是一个节点——》

这步其实分两种,如果是值,那么就是执行step4,获取值的字窜,如果是子节点呢,我们一看就知道,它又是进行了step2,

即读取到头标签了,其实你是很人读一片文章流程一样,只不过我们脑中有个印象<xxx>是头标签了,我们要做什么,独到 头标签的最后一个符号">"

下面进去值域,独到了字窜的话就调用了foundCharacters:(NSString *)string,如果又读到<xxx>这样的,那就又是头标签了。——》

step5就是读到开始尾标签符号了。

最后一个方法

foundCDATA:(NSData *)CDATABlock,其实也是一个格式


要解析的xml如下

<?xml version="1.0" encoding="UTF-8"?>
<postTypes>
    <postType name="计算机硬件">
        <child code="2401" name="高级硬件工程师"></child>
        <child code="2402" name="硬件工程师"></child>
        <child code="2403" name="其他"></child>
    </postType>
    <postType name="计算机软件">
        <child code="0106" name="高级软件工程师"></child>
        <child code="0107" name="软件工程师"></child>
    </postType>
    <postType name="互联网开发及应用">
        <child code="2501" name="互联网软件开发工程师"></child>
    </postType>
    
</postTypes>

解析方法

#import "ViewController.h"

@interface ViewController ()<NSXMLParserDelegate>
{
    NSMutableDictionary *Objectdic;
    NSMutableDictionary *NameClassdic;
    NSMutableArray *Object;
    NSString *class;
}
@end

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];
    
#pragma mark 输出返回的xml值
    NSString *Path = [[NSBundle mainBundle]pathForResource:@"post_type" ofType:@"xml"];
    NSInputStream *Input = [NSInputStream inputStreamWithFileAtPath:Path];
    NSXMLParser *xml = [[NSXMLParser alloc]initWithStream:Input];
    xml.delegate = self;
    [xml setShouldProcessNamespaces:NO];
    [xml setShouldReportNamespacePrefixes:NO];
    [xml setShouldResolveExternalEntities:NO];
    [xml setDelegate:self];
    [xml parse];
    
    NSLog(@"dic  is  %@", NameClassdic);
}

/**
 *  已经开始解析
 *
 */
- (void)parserDidStartDocument:(NSXMLParser *)parser
{
    NameClassdic = [NSMutableDictionary dictionary];
}

#pragma mark 遍例xml的节点,执行以下代理方法
-(void)parser:(NSXMLParser *)parser didStartElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName attributes:(NSDictionary *)attributeDict {
    
    
    if ([elementName isEqualToString:@"child"]) { // child 里面的值
        
        [Object addObject:attributeDict];
        [NameClassdic removeObjectForKey:class];
        if (![NameClassdic valueForKey:class]) {
            [NameClassdic setObject:Object forKey:class];
        }
        
    }else{
        if ([elementName isEqualToString:@"postType"]) {
            if (NameClassdic.count != 0) {
                
            }
            class = attributeDict[@"name"];
            Object = [NSMutableArray array];
        }
        
        
    }
    
}

//step 3:获取首尾节点间内容
- (void)parser:(NSXMLParser *)parser foundCharacters:(NSString *)string{
}

//step 4 :解析完当前节点
- (void)parser:(NSXMLParser *)parser didEndElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName{
    
}

//step 5;解析结束
- (void)parserDidEndDocument:(NSXMLParser *)parser
{
    
}

//获取cdata块数据
- (void)parser:(NSXMLParser *)parser foundCDATA:(NSData *)CDATABlock
{
    
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值