`
yesjavame
  • 浏览: 689349 次
  • 性别: Icon_minigender_2
  • 来自: 杭州
文章分类
社区版块
存档分类
最新评论

用正则表达式解析XML文档

阅读更多

这段时间做中移动的一些接口,看到那些"标准接口"心里不知道是什么感觉.连笑都懒得笑了.

一个连26个字母都认不全的人,说我要做英语同声翻译,说这种话除了需要天大的勇气,其它的只能说是无知了.连一些java的基础语法都不能正确应用,竟然写出给"中国移动"这种绝对企业级应用的接口,中兴公司开发的MM7接口,看了以后每一个有良心的程序员都有想自杀的感觉.

算了,不提它了.

目前在java平台上,要解析xml文档,即使只有"<abc></abc>"这样的一个标签,在生成document对象时,也至少要花费300ms左右,这样一次交互至少要在600ms左右,加上其它处理,一次通讯要1000ms以上,使得soap协议在java平台上根本不能进行实际应用.

其它这并不是SOAP协议的问题,着关键在于对XML文档的解析.基于这个原因,笔者实现了用正则表达式来解析XML文档的一些API,利用它来在替换中移动的大多数SOAP的接口,效率提高了10倍左右.

package org.axman.xml.regex;

import java.util.regex.*;
import java.util.*;

/**
*
* <p>Title: Document</p>
*
* <p>Description: 用正则表达式解析xml,目的是为了提高性能.</p>
*
* <p>Copyright: Copyright (c) 2005</p>
*
* <p>Company: org.axman</p>
*
* @author :Axman
* @version 1.0
*/
public class Document {
private String xmlString;

/**
* 传入xml的字符串内容,对于InputStream,Reader对象请转换为String对象后传入构造方法.
* @param xmlString String
* @throws IllegalArgumentException
*/
public Document(String xmlString) throws IllegalArgumentException{
if(xmlString == null || xmlString.length() == 0)
throw new IllegalArgumentException("Input string orrer!");
this.xmlString = xmlString;
}


/**
* 在文档中搜索指定的元素,返回符合条件的元素数组.
* @param tagName String
* @return String[]
*/
public String[] getElementsByTag(String tagName){
Pattern p = Pattern.compile("<"+tagName+"[^>]*?((>.*?</"+tagName+">)|(/>))");
Matcher m = p.matcher(this.xmlString);
ArrayList<String> al = new ArrayList<String>();
while(m.find())
al.add(m.group());
String[] arr = al.toArray(new String[al.size()]);
al.clear();
return arr;
}


/**
* 用xpath模式提取元素,以#为分隔符
* 如 ROOT#PARENT#CHILD表示提取ROOT元素下的PARENT元素下的CHILD元素
* @param singlePath String
* @return String
*/
public String getElementBySinglePath(String singlePath){
String[] path = singlePath.split("#");
String lastTag = path[path.length-1];
String tmp = "(<"+lastTag+"[^>]*?((>.*?</"+lastTag+">)|(/>)))";
//最后一个元素,可能是<x>v</x>形式或<x/>形式
for(int i=path.length-2;i >=0;i--){
lastTag = path[i];
tmp = "<"+lastTag+">.*"+tmp + ".*</"+lastTag+">";
}
Pattern p = Pattern.compile(tmp);
Matcher m = p.matcher(this.xmlString);
if(m.find()){
return m.group(1);
}
return "";
}

/**
* 用xpath模式提取元素从多重元素中获取指批定元素,以#为分隔符
* 元素后无索引序号则默认为0: ROOT#PARENT[2]#CHILD[1]
* @param singlePath String
* @return String
*/
public String getElementByMultiPath(String singlePath){
try{
String[] path = singlePath.split("#");
String input = this.xmlString;
String[] ele = null;
for (int i = 0; i < path.length; i++) {
Pattern p = Pattern.compile("(\\w+)(\\[(\\d+)\\])?");
Matcher m = p.matcher(path[i]);
if (m.find()) {
String tagName = m.group(1);
System.out.println(input + "----" + tagName);
int index = (m.group(3) == null) ? 0 :
new Integer(m.group(3)).intValue();
ele = getElementsByTag(input, tagName);
input = ele[index];
}
}
return input;
}catch(Exception e){
return null;
}
}

/**
* 在给定的元素中搜索指定的元素,返回符合条件的元素数组.对于不同级别的同名元素限制作用,即可以
* 搜索元素A中的子元素C.而对于元素B中子元素C则过虑,通过多级限定可以准确定位.
* @param parentElementString String
* @param tagName String
* @return String[]
*/
public static String[] getElementsByTag(String parentElementString,String tagName){
Pattern p = Pattern.compile("<"+tagName+"[^>]*?((>.*?</"+tagName+">)|(/>))");
Matcher m = p.matcher(parentElementString);
ArrayList<String> al = new ArrayList<String>();
while(m.find())
al.add(m.group());
String[] arr = al.toArray(new String[al.size()]);
al.clear();
return arr;
}

/**
* 从指定的父元素中根据xpath模式获取子元素,singlePath以#为分隔符
* 如 ROOT#PARENT#CHILD表示提取ROOT元素下的PARENT元素下的CHILD元素
* @param parentElementString String
* @param singlePath String
* @return String
*/
public static String getElementBySinglePath(String parentElementString,String singlePath){
String[] path = singlePath.split("#");
String lastTag = path[path.length-1];
String tmp = "(<"+lastTag+"[^>]*?((>.*?</"+lastTag+">)|(/>)))";
//最后一个元素,可能是<x>v</x>形式或<x/>形式
for(int i=path.length-2;i >=0;i--){
lastTag = path[i];
tmp = "<"+lastTag+">.*"+tmp + ".*</"+lastTag+">";
}
Pattern p = Pattern.compile(tmp);
Matcher m = p.matcher(parentElementString);
if(m.find()){
return m.group(1);
}
return "";
}

/**
* 用xpath模式提取元素从指定的多重元素中获取指批定元素,以#为分隔符
* @param parentElementString String
* @param singlePath String
* @return String
*/
public static String getElementByMultiPath(String parentElementString,String singlePath){
try{
String[] path = singlePath.split("#");
String input = parentElementString;
String[] ele = null;
for (int i = 0; i < path.length; i++) {
Pattern p = Pattern.compile("(\\w+)(\\[(\\d+)\\])?");
Matcher m = p.matcher(path[i]);
if (m.find()) {
String tagName = m.group(1);
int index = (m.group(3) == null) ? 0 :
new Integer(m.group(3)).intValue();
ele = getElementsByTag(input, tagName);
input = ele[index];
}
}
return input;
}catch(Exception e){
return null;
}
}


/**
* 在给定的元素中获取所有属性的集合.该元素应该从getElementsByTag方法中获取
* @param elementString String
* @return HashMap
*/
public HashMap<String,String> getAttributes(String elementString){
HashMap hm = new HashMap<String,String>();
Pattern p = Pattern.compile("<[^>]+>");
Matcher m = p.matcher(elementString);
String tmp = m.find()?m.group():"";
p = Pattern.compile("(\\w+)\\s*=\\s*\"([^\"]+)\"");
m = p.matcher(tmp);
while(m.find()){
hm.put(m.group(1).trim(),m.group(2).trim());
}
return hm;
}


/**
* 在给定的元素中获取指定属性的值.该元素应该从getElementsByTag方法中获取
* @param elementString String
* @param attributeName String
* @return String
*/
public static String getAttribute(String elementString,String attributeName){
HashMap hm = new HashMap<String,String>();
Pattern p = Pattern.compile("<[^>]+>");
Matcher m = p.matcher(elementString);
String tmp = m.find()?m.group():"";
p = Pattern.compile("(\\w+)\\s*=\\s*\"([^\"]+)\"");
m = p.matcher(tmp);
while(m.find()){
if(m.group(1).trim().equals(attributeName))
return m.group(2).trim();
}
return "";
}


/**
* 获取指定元素的文本内容
* @param elementString String
* @return String
*/
public static String getElementText(String elementString){
Pattern p = Pattern.compile(">([^<>]*)<");
Matcher m = p.matcher(elementString);
if(m.find()){
return m.group(1);
}
return "";
}

public static void main(String[] args){
new Document("<ROOT>sss <PARENT>sss <CHILD>aaaa</CHILD>ss </PARENT>sss </ROOT>").getElementByMultiPath("ROOT[0]#PARENT#CHILD");
//System.out.println(child);
}

}

分享到:
评论

相关推荐

    正则表达式+xml

    结合提供的`RegexTool`文件,这可能是一款集成了正则表达式验证和XML操作功能的工具,用户可以利用它来测试正则表达式,或者处理XML文档,比如验证XML的结构、提取XML数据等。这样的工具对于开发者来说非常实用,...

    xml需求文档及正则表达式介绍

    结合XML和正则表达式,我们可以用正则表达式来解析和验证XML文档中的数据。例如,可以用正则表达式匹配XML元素的名称,或者从XML文本中提取特定属性值。然而,对于复杂的XML结构,通常会使用解析库(如Python的lxml...

    XML正则表达式 工具

    通过学习这个教程,你可以快速掌握正则表达式的基础,并使用RegexTester.exe进行实践,从而更有效地处理XML文档中的数据。在XML中应用正则表达式时,要注意XML的特殊性,比如需要考虑到XML的标签结构、属性值的引号...

    正则表达式+XML指南

    例如,在XML文档中搜索特定模式,可以用正则表达式来定位和提取数据;XML解析器也可能使用正则表达式来验证某些属性值或元素内容。同时,XML Schema中的Pattern约束也可以使用正则表达式来限制元素的值。 综上所述...

    正则表达式综合练习

    在网络爬虫中,它可以用于解析HTML或XML文档,提取链接、文本内容等。 10. **编程语言支持**:大多数编程语言都内置了正则表达式支持,如Java(Test.java中的例子可能涉及Java的`Pattern`和`Matcher`类),Python的...

    Web数据抓取中的正则表达式解析2022优秀文档.pptx

    在Web数据抓取中,正则表达式通常与网络爬虫结合使用,帮助从HTML或XML页面中提取特定的数据,如电子邮件地址、电话号码、文章标题等。通过编写合适的正则表达式,我们可以精确地定位并提取所需的信息,从而自动化...

    正则表达式-文档和网页

    - **HTML 与 XML 标签处理**: 可以用正则表达式匹配和提取 HTML 或 XML 标签,进行解析和清洗。 - **爬虫与数据提取**: 在网络爬虫中,正则表达式是抓取网页数据的重要工具,例如,使用 `\d+` 提取网页上的价格...

    JS的正则表达式进行验证

    在这些场景下,正则表达式可以帮助开发者检查加载的数据是否符合预期的结构或格式,比如检查JSON数据的完整性,或验证从服务器返回的XML文档中的元素名称。 ### 结论 综上所述,正则表达式在JavaScript中的应用...

    XML正则表达式转换工具

    在处理XML文档时,有时我们可能需要使用正则表达式来匹配或提取特定的数据。正则表达式是模式匹配的强大工具,能够有效地查找、替换和解析文本。 "XML正则表达式转换工具"可能是一个专门设计用于处理XML文档中的...

    Java基于正则表达式实现xml文件的解析功能详解

    Java基于正则表达式实现xml文件的解析功能是指使用Java语言结合正则表达式来解析xml文件的技术。正则表达式是一种强大的字符串匹配模式,可以用来匹配xml文件中的节点和属性。本文将详细介绍Java基于正则表达式实现...

    正则表达式趣味例子集合

    - 在网页爬虫中,它们用于解析HTML和XML文档,抓取需要的信息。 - 在代码中,它们可以用于输入验证、数据清洗和格式化。 6. **正则表达式的性能与优化** - 长度优先原则:正则引擎通常优先尝试最短的匹配方式,...

    正则表达式处理html文本例子

    9. **学习资源**:为了深入理解和使用正则表达式,可以参考在线教程,如RegExr、MDN Web Docs上的正则表达式指南,或者C#的官方文档。 通过理解以上知识点,你将能够运用正则表达式有效地处理HTML文本,无论是简单...

    PHP用正则表达式过滤超链接

    在PHP中,正则表达式的应用非常广泛,特别是在处理HTML或XML等结构化文档时。下面是一些常用的正则表达式语法: - `.`:匹配任意单个字符(除了换行符)。 - `*`:前面的表达式可以出现任意次,包括0次。 - `+`:...

    正则表达式-入门培训

    ### 正则表达式入门培训知识点详解 ...以上是对正则表达式的基础概念及常见应用场景的介绍,通过实例展示了如何使用正则表达式来解决实际问题。希望这些知识点能够帮助初学者更好地理解和掌握正则表达式的使用技巧。

    xml+正则表达式(chm)

    正则表达式(Regular Expression),简称regex,是一种模式匹配工具,用于在文本中查找、替换或提取符合特定模式的字符串。它由各种字符和特殊符号组成,可以实现复杂的字符串匹配和操作。正则表达式在编程语言、...

    网页抓取 正则表达式 前台处理json对象

    综上所述,这个项目可能涉及到使用网页抓取技术获取网页数据,然后利用正则表达式清洗和解析数据。在前端部分,可能通过AJAX请求获取后端服务的JSON数据,并在页面上进行实时更新和展示。如果涉及到跨域问题,可能...

    java正则表达式全

    5. **网络数据解析**:在处理HTTP响应或XML、JSON数据时,可以利用正则表达式提取特定字段。 四、正则表达式帮助文档 为了更好地理解和使用Java正则表达式,官方提供的帮助文档是非常宝贵的资源。它包含了详细的...

    方便测试的正则表达式小工具

    在正则表达式小工具中,它可能被用来解析和操作XML文档,可能包含用户输入的正则表达式和测试数据。 2. Collector.dll、Spider.dll:这两个文件可能涉及到数据采集或网络爬虫的功能,可能被用作测试正则表达式在实际...

Global site tag (gtag.js) - Google Analytics