java解析超大xml并插入数据库

wo401554998 2013-08-24 07:00:36
各位你们好,小弟今年刚毕业,学习java不久,到一家小公司上班,boss给我的任务是从xml文件中解析出表名、字段名、以及字段的值,把他插入到mysql相同的表中去,他设计的表呢有个问题,(1)数据库表中字段比我解析的字段多,有些字段我这个xml没有,这好说,不插入就行了,(2)字段比我解析出来的字段少,这就麻烦了,我如何插入数据库呢?哦我用的是jdbc xml文件目前是40M ,过几天可能会有更大,mysql的表示200多个, 介于问题二 苦恼了好几天不会解决求大神帮忙。再次谢过,我积分不多希望别介意
xml部分信息

<?xml version="1.0" encoding = "gbk"?>
<rdf:RDF xml:base="nari" xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" xmlns:cim="http://iec.ch/TC57/2003/CIM-schema-cim10#" xmlns:cimNARI="http://www.naritech.cn/CIM/ext-schema#">
<cim:SubControlArea rdf:ID="209000001">
<cim:Naming.name>乐平市供电公司</cim:Naming.name>
<cimNARI:SubControlArea.areaNo>1</cimNARI:SubControlArea.areaNo>
<cimNARI:SubControlArea.recordApp>2031647</cimNARI:SubControlArea.recordApp>
<cimNARI:SubControlArea.MemberOf_ControlArea rdf:resource="#209000007"/>
</cim:SubControlArea>
<cim:BaseVoltage rdf:ID="200000003">
<cimNARI:BaseVoltage.name>110</cimNARI:BaseVoltage.name>
<cim:BaseVoltage.nominalVoltage>110.000000</cim:BaseVoltage.nominalVoltage>
<cimNARI:BaseVoltage.nominalI>0.000000</cimNARI:BaseVoltage.nominalI>
<cimNARI:BaseVoltage.v_exm>132.000000</cimNARI:BaseVoltage.v_exm>
<cimNARI:BaseVoltage.mva_exm>305.000000</cimNARI:BaseVoltage.mva_exm>
</cim:BaseVoltage>
<cim:Substation rdf:ID="210000048">
<cim:Naming.name>饶丰变</cim:Naming.name>
<cim:Naming.aliasName>饶丰变</cim:Naming.aliasName>
<cimNARI:Substation.substationType rdf:resource="http://www.naritech.cn/CIM/ext-schema#SubstationType.trans"/>
<cimNARI:Substation.recordApp>2031647</cimNARI:Substation.recordApp>
<cimNARI:Substation.MaxBaseVoltage rdf:resource="#200000004"/>
<cim:Substation.MemberOf_SubControlArea rdf:resource="#209000003"/>
</cim:Substation>
<cim:Measurement rdf:ID="03060009610010">
<cim:Naming.name>马302过流II段</cim:Naming.name>
<cim:Measurement.MeasurementType rdf:resource="#372000022"/>
<cimNARI:Measurement.RelaySignal rdf:resource="#306000961"/>
<cim:Measurement.MemberOf_PSR rdf:resource="#210000065"/>
</cim:Measurement>
<cim:Measurement rdf:ID="03070020190010">
<cim:Measurement.maxValue>0.000000</cim:Measurement.maxValue>
<cim:Measurement.minValue>0.000000</cim:Measurement.minValue>
<cim:Naming.name>茶山变_10kV天鹅一路线线电压BC相 </cim:Naming.name>
<cim:Measurement.MeasurementType rdf:resource="#372000032"/>
<cimNARI:Measurement.MeasValue rdf:resource="#307002019"/>
<cim:Measurement.MemberOf_PSR rdf:resource="#210000083"/>
</cim:Measurement>
</rdf:RDF>


就以第一个节点为例吧,SubControlArea是表名,ID、name、areaNo、recordApp、resource是字段。

java代码(我现在能解析出表名,字段不会弄,会的话给我说下谢谢)

/*
* To change this template, choose Tools | Templates
* and open the template in the editor.
*/
package ly.pconline.com.cn.utils.xml.dom4j;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.Iterator;
import java.util.List;
import org.dom4j.Document;
import org.dom4j.Element;
import org.dom4j.ElementHandler;
import org.dom4j.ElementPath;
import org.dom4j.io.SAXReader;

/**
*
* @author liyong
*/
public class XindexReader1 {

public static int flag = 0;

public static void main(String[] args) {
XindexReader1 x = new XindexReader1();
// x.parseXml();
x.parseXml2();
}

public void parseXml() {
SAXReader saxReader = new SAXReader();
InputStream in = null;

try {
File file = new File("E:\\work123.xml");
in = new FileInputStream(file);
ElementHandler myHandler = new ElementHandler() {
@Override
public void onStart(ElementPath ep) {
// System.out.println("www");
}

@Override
public void onEnd(ElementPath ep) {
Element element = ep.getCurrent(); // 获得当前节点
String en = element.getName();
System.out.println(en);
}
};
saxReader.addHandler("/RDF", myHandler);
saxReader.addHandler("/RDF/Substation", myHandler);
// saxReader.resetHandlers();
saxReader.read(in);
} catch (Exception e) {
e.printStackTrace();
} finally {
if (in != null) {
try {
in.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}

public void parseXml2() {
SAXReader saxReader = new SAXReader();
InputStream in = null;
try {
File file = new File("E:\\work123.xml");
in = new FileInputStream(file);
Document doc = saxReader.read(in);
List modelList = doc.selectNodes("//RDF");//以每个model划分
Iterator its = modelList.iterator();
int i = 0;
while (its.hasNext()) {
Element element = (Element) its.next();
Iterator it = element.elementIterator();
while (it.hasNext()) {
Element et = (Element) it.next();
String key = et.getName();
i++;
System.out.println(key + ":" + i);
}


}
} catch (Exception e) {
e.printStackTrace();
} finally {
if (in != null) {
try {
in.close();
} catch (IOException e) {
}
}
}

}
}


哦,我大概说下我的苦恼吧,xml解析出来应该是一表为单位,然后从mysl中的表信息去核对,把我解析多的字段去除,然后插入进去。不知道我的思路可否正确 ,哦同时boss设计的表其中的字段是不允许我随意修改的
...全文
741 19 打赏 收藏 转发到动态 举报
写回复
用AI写文章
19 条回复
切换为时间正序
请发表友善的回复…
发表回复
wo401554998 2013-08-28
  • 打赏
  • 举报
回复
引用 18 楼 wenjie4892543 的回复:
(1)数据库表中字段比我解析的字段多,有些字段我这个xml没有,这好说,不插入就行了, (2)数据库字段比我解析出来的字段少 这2个我不是很明白,,, ex: 数据库 字段 有 name sex age 你解析的xml字段有 name address phone 那你就只insert一个name就行了,难度你还管 address 和 phone 么?
对的
wenjie4892543 2013-08-28
  • 打赏
  • 举报
回复
(1)数据库表中字段比我解析的字段多,有些字段我这个xml没有,这好说,不插入就行了, (2)数据库字段比我解析出来的字段少 这2个我不是很明白,,, ex: 数据库 字段 有 name sex age 你解析的xml字段有 name address phone 那你就只insert一个name就行了,难度你还管 address 和 phone 么?
wenjie4892543 2013-08-28
  • 打赏
  • 举报
回复
Dom4jReadExmple.java

package dom4j;

import java.io.File;
import java.util.HashMap;
import java.util.Iterator;

import org.dom4j.Attribute;
import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.Element;
import org.dom4j.io.SAXReader;
/**
 * 利用dom4j进行XML编程
 * @author cuiweibing
 * @since 2007.8.10
 */
public class Dom4jReadExmple {
 /**
  * 遍历整个XML文件,获取所有节点的值与其属性的值,并放入HashMap中
  * @param filename String 待遍历的XML文件(相对路径或者绝对路径)
  * @param hm       HashMap 存放遍历结果,格式:<nodename,nodevalue>或者<nodename+attrname,attrvalue>
  */
 public void iterateWholeXML(String filename,HashMap<String,String> hm){
  SAXReader saxReader = new SAXReader();
  try {
   Document document = saxReader.read(new File(filename));
   Element root = document.getRootElement();
//   用于记录学生编号的变量
   int num=-1;
   //遍历根结点(students)的所有孩子节点(肯定是student节点)
         for ( Iterator iter = root.elementIterator(); iter.hasNext(); ) {
             Element element = (Element) iter.next();
             num++;
    // 获取person节点的age属性的值
             Attribute ageAttr=element.attribute("age");
    if(ageAttr!=null){
     String age = ageAttr.getValue();
     if (age != null&&!age.equals("")) {
      hm.put(element.getName() + "-"+ageAttr.getName()+ num, age);
     } else {
      hm.put(element.getName() + "-" +ageAttr.getName()+ num, "20");
     }
    }else{
     hm.put(element.getName() + "-age"+ num, "20");
    }
             //遍历student结点的所有孩子节点(即name,college,telphone,notes),并进行处理
             for ( Iterator iterInner = element.elementIterator(); iterInner.hasNext(); ) {
              Element elementInner = (Element) iterInner.next();
              if(elementInner.getName().equals("college")){
               hm.put(elementInner.getName()+ num, elementInner.getText());
               //获取college节点的leader属性的值
               Attribute leaderAttr=elementInner.attribute("leader");
               if(leaderAttr!=null){
       String leader = leaderAttr.getValue();
       if (leader != null&&!leader.equals("")) {
        hm.put(elementInner.getName() + "-"+leaderAttr.getName()+ num, leader);
       } else {
        hm.put(elementInner.getName() + "-" +leaderAttr.getName()+ num, "leader");
       }
               }else {
       hm.put(elementInner.getName() + "-leader"+ num, "leader");
      }
              }else{
               hm.put(elementInner.getName()+ num, elementInner.getText());
              }
             }
         }

  } catch (DocumentException e) {
   // TODO Auto-generated catch block
   e.printStackTrace();
  }
 }
}

package dom4j;

import java.util.HashMap;

/**
 * 测试Dom4jReadExmple解析的情况
 * @author cuiweibing
 * @since 2007.8.10
 */
public class TestDom4jReadExmple {
 public static void main(String[] args) {
     try{
       //获取解析完后的解析信息
       HashMap<String,String> hashMap;
       Dom4jReadExmple drb=new Dom4jReadExmple();
       //遍历整个XML文件
       hashMap = new HashMap<String,String>();
       drb.iterateWholeXML("D:\\studentInfo.xml", hashMap);
       System.out.println("姓名/t年龄/t学院/t学院领导/t电话/t/t备注");
       for(int i=0;i<hashMap.size();i+=6){
         int j=i/6;
         System.out.print(hashMap.get("name"+j)+"/t");
         System.out.print(hashMap.get("student-age"+j)+"/t");
         System.out.print(hashMap.get("college"+j)+"/t");
         System.out.print(hashMap.get("college-leader"+j)+"/t");
         System.out.print(hashMap.get("telephone"+j)+"/t");
         System.out.println(hashMap.get("notes"+j)+"/t");
       }
     }catch(Exception ex){
       ex.printStackTrace();
     }
   }
}


<?xml version="1.0" encoding="gb2312"?>
<students>
    <student age="25"><!--如果没有age属性,默认的为20-->
        <college>PC学院</college>
        <telephone>62354666</telephone>
        <notes>男,1982年生,硕士,现就读于北京邮电大学</notes>
    </student>
    <student>
        <name>cwb</name>
        <college leader="学院领导">PC学院</college><!--如果没有leader属性,默认的为

leader-->
        <telephone>62358888</telephone>
        <notes>男,1987年生,硕士,现就读于中国农业大学</notes>
    </student>
    <student age="45">
        <name>xxxxx</name>
        <college leader="">xxx学院</college>
        <telephone>66666666</telephone>
        <notes>注视中,注释中</notes>
    </student>
    <student age="">
        <name>lxx</name>
        <college>yyyy学院</college>
        <telephone>88888888</telephone>
        <notes>注视中111,注释中222</notes>
    </student>
</students>
TCL5409 2013-08-28
  • 打赏
  • 举报
回复
我的第一个任务也是解析xml并导入数据库,64M的文件,不过就两列,嘿嘿
TCL5409 2013-08-28
  • 打赏
  • 举报
回复
楼主是插入一张表吧,那这张表跟你解析出来的字段多呢还是少呢?
wo401554998 2013-08-26
  • 打赏
  • 举报
回复
引用 13 楼 wufengui1315 的回复:
对于第二个问题:数据库字段比解析的字段少,两种理解:1.对与有的字段就进行插入操作,没有的字段不做任何处理;2.有的字段插入操作,没有的字段添加字段在插入数据。貌似楼主是第一种。最直接的思路就是写一个方法判断有没有这个字段,有这个字段则进行操作。当然或对效率又影响。
对的,13楼说的很对,现在的问题是怎么判断,取出所有表的字段,还是一个表一个表慢慢来呢,呵呵。是比较复杂,也没来个大神解决下
末日哥 2013-08-25
  • 打赏
  • 举报
回复
不可以把你解析出来的数据先放在一个Map里面,再根据Key值插入到对应的列吗
jongsuny 2013-08-25
  • 打赏
  • 举报
回复
用dom解析是肯定不行的,可以尝试sax方式。 如果不行就把java的运行内存调到最大,这样也出现oom的话就把文件分割,分割成更小的单位, 让内存容得下, 是在不行就楼上说的IO方式。
coooliang 2013-08-25
  • 打赏
  • 举报
回复
你搜一下解析XML的插件吧,dom4j,sax什么的。 要把XML看成一棵树再解析。
zqfddqr 2013-08-25
  • 打赏
  • 举报
回复
引用 6 楼 wo401554998 的回复:
[quote=引用 4 楼 evangelionxb 的回复:] 你这个工作量太大了。 (2)字段比我解析出来的字段少,这就麻烦了,我如何插入数据库呢? 这个问题主动去和老板沟通,程序员的技能不光仅仅在于编码! 这个xml解析我考虑jaxb,但是由于我也不太熟悉,还有最近很忙, 估计按jaxb很慢才能实现出来。 实在不行就 io + 正则解析。
嗯谢谢的回复,正则我去看看吧[/quote]我去 可别正则解析 jom4j就OK了 沟通一下字段插入就完了
wasdasdfqwer 2013-08-25
  • 打赏
  • 举报
回复
对于第二个问题:数据库字段比解析的字段少,两种理解:1.对与有的字段就进行插入操作,没有的字段不做任何处理;2.有的字段插入操作,没有的字段添加字段在插入数据。貌似楼主是第一种。最直接的思路就是写一个方法判断有没有这个字段,有这个字段则进行操作。当然或对效率又影响。
a406979945 2013-08-25
  • 打赏
  • 举报
回复
jaxb解析还是可以的,映射下就好的
wo401554998 2013-08-25
  • 打赏
  • 举报
回复
引用 4 楼 evangelionxb 的回复:
你这个工作量太大了。 (2)字段比我解析出来的字段少,这就麻烦了,我如何插入数据库呢? 这个问题主动去和老板沟通,程序员的技能不光仅仅在于编码! 这个xml解析我考虑jaxb,但是由于我也不太熟悉,还有最近很忙, 估计按jaxb很慢才能实现出来。 实在不行就 io + 正则解析。
嗯谢谢的回复,正则我去看看吧
evangelionxb 2013-08-25
  • 打赏
  • 举报
回复
具体相关博客你可以自己搜搜 http://blog.csdn.net/axman/article/details/420910
evangelionxb 2013-08-25
  • 打赏
  • 举报
回复
你这个工作量太大了。 (2)字段比我解析出来的字段少,这就麻烦了,我如何插入数据库呢? 这个问题主动去和老板沟通,程序员的技能不光仅仅在于编码! 这个xml解析我考虑jaxb,但是由于我也不太熟悉,还有最近很忙, 估计按jaxb很慢才能实现出来。 实在不行就 io + 正则解析。
wo401554998 2013-08-25
  • 打赏
  • 举报
回复
饿 没有一个整体的思路
wo401554998 2013-08-25
  • 打赏
  • 举报
回复
回复一楼 当然是没有的了 二楼 sax是流处理可是她过于低端,处理是有点慢的 和sax相同解析模式的是stax 你感兴趣的话可以看下 我在一块用的dom4j
nonocd 2013-08-24
  • 打赏
  • 举报
回复
也是毕业生,还在失业中,xml解析你可以试试使用DOM来解析,或者SAX。DOM在解析的时候会把整个XML文档全部映射为Document里的树状结构,对于小文件很方便,但是文档很大时,对内存占用较大、速度较慢。SAX解析器从XML文档开始位置进行解析,同时根据定义好的事件处理器,决定当前所解析的部分是否记录、存储,这个的运用我也不熟悉。还有就是使用JAXB,把xml与Java类映射来解析数据。我也是菜鸟,共同学习,不知道对楼主有没有帮助,不对之处勿喷。。。。
2013-08-24
  • 打赏
  • 举报
回复
感觉好麻烦。你有在在数据库中添加字段的权限么。

67,518

社区成员

发帖
与我相关
我的任务
社区描述
J2EE只是Java企业应用。我们需要一个跨J2SE/WEB/EJB的微容器,保护我们的业务核心组件(中间件),以延续它的生命力,而不是依赖J2SE/J2EE版本。
社区管理员
  • Java EE
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧