前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >为什么LINQ to XML的性能要优于XmlDocument?

为什么LINQ to XML的性能要优于XmlDocument?

作者头像
雪雁-心莱科技
发布2018-12-27 10:44:49
1.1K0
发布2018-12-27 10:44:49
举报
文章被收录于专栏:magicodesmagicodesmagicodes

一直很忙,压了很多贴,今天发一篇吧。后面的看心情吧。

今天群里有人问如何解析web.config方便,然后我就推荐了Linq to XML,然后就有人说“我宁可XmlDocument,再SeleteNodes和SeleteNode”,不要用LINQ之类的,甚至否定EntityFramework等一系列框架,认为这些都是所谓的“懒人技术”,都是以牺牲性能为代价的。我在这里想申明一点,没有测试就没有发言权,并不是所有的”懒人技术“都是以牺牲性能为代价的。我这人比较喜欢就技术论技术,不喜欢武断的言论,于是展开了讨论。本文只是做一个总结。

LINQ to XML的性能测试

很多同学已经做过性能测试了,我就不重复了,如下链接:

XML数据读取方式性能比较(一)

XML数据读取方式性能比较(二)

从上面的结果我们不能看出,Linq to Xml的性能明显是优于XmlDocument的。我这人比较喜欢追根溯源,如果单从这个,总是有人会产生各种悖论,比如:

【码帅】-------- 13:52:01 确定真是LINQ高吗 【码奴】-------- 13:52:32 什么高? 【码帅】-------- 13:52:42 为什么上面2个都有Add 【码帅】-------- 13:52:49 下面2个都没有 【码帅】-------- 13:52:54 这测试公正吗 【码帅】-------- 13:53:18 好比一个是直接new Object[] 【码帅】-------- 13:54:38 4个测试就有问题 【码帅】-------- 13:56:03 2个40多秒的都有这Add

其实他的问题都没到点上,这里根本就不是Add的问题,Linq的ToList()方法肯定也干了这事,如果怀疑这里,完全可以自己去写个测试。所以我觉得有必要说下为什么LINQ to XML性能优于XmlDocument的缘由了。

为什么LINQ to XML性能优于XmlDocument?

首先,我们需要明白的一点是:

LINQ to XML有一位优秀的母亲——XmlReader。

LINQ to XML 在 XmlReader 基础之上实现的,也就是LINQ to XML源于XmlReader,高于XmlReader。

遗传基因很重要!

XmlReader 是一种快速的只进非缓存分析器。他丫的对XML 数据流的访问是只读的。

其次,LINQ to XML有一位出色的父亲——Linq。

LINQ to XML 的一个最重要的性能优势(与 XmlDocument 相比)为:LINQ to XML 中的查询是静态编译的,而 XPath 查询则必须在运行时进行解释。

这个因素是性能中至关重要的,所谓”子不教,父之过“!

也就是说,LINQ to XML的查询被编译成静态链接的方法调用,这样的性能提升是巨大的。反观XmlDocument,它在每次调用 SelectNodes 方法时,都必须在内部执行以下操作:

  1. 分析包含 XPath 表达式的字符串,并将字符串划分成多个标记。
  2. 验证这些标记以确保 XPath 表达式有效。
  3. 将表达式转换为内部表达式树。
  4. 循环访问节点,为基于表达式计算的结果集选择适当的节点。

与相应的 LINQ to XML 查询完成的工作相比,这需要执行非常多的工作。

除此之外,LINQ to XML还继承了父亲的延迟执行的优良传统,也能够提高性能。

父亲这么优秀,XmlDocument自然无法相比了。

所以,富二代和官二代起点就比你高,你如果不比他们多付出N倍的努力,你甚至连他们的起点都无法到达。

科普下延迟执行的知识:

延迟执行意味着表达式的计算延迟,直到真正需要它的实现值为止。 当必须操作大型数据集合,特别是在包含一系列链接的查询或操作的程序中操作时,延迟执行可以大大改善性能。 在最佳情况下,延迟执行只允许对源集合的单个循环访问。 LINQ 技术广泛应用了延迟执行,包括在核心 System.Linq 类的成员和不同 LINQ 命名空间中的扩展方法(如 System.Xml.Linq.Extensions)中使用。

除了上面的,其他的还有些他在成长过程中,自己提升的优点,比如:XName 和 XNamespace 对象是原子化的,如果这两个对象包含相同的名字,则它们会引用同一个对象。 也就是说当比较两个原子化名称是否相等时,只需确定这两个引用是否指向同一个对象,而不必进行很”耗费时间“的字符串比较,这个是有助于性能提升的。

尾声

虽然这不是拍电影,但是尾声还是必须的。

  1. 没有测试就没有发言权,并不是所有的”懒人技术“都是以牺牲性能为代价的
  2. 虽然Linq to SQL的名声不大好,但是LINQ to XML却应该是实至名归。而且Linq to SQL的儿子EF正在挽回她的名声,如果你没用过,请不要说他不行,如果你用的不当,请也别说他不行。
  3. 懒人技术都是懒人发明的,但是往往就是这些懒人推动了技术的前进。
  4. 每一种技术和框架都是有使用场景的,如果你用错了场景,请不要说他不行。
  5. 合理把控性能,在大多数非苛刻场景,不到1毫秒甚至更多的差别,你完全不必要浪费1小时以上的精力,认真提高开发效率才是关键的。比如枚举类型的ToString()。
本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2014-07-21 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • LINQ to XML的性能测试
    • XML数据读取方式性能比较(二)
    • 为什么LINQ to XML性能优于XmlDocument?
    • 尾声
    领券
    问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档