我从API
获取XML数据数据类似于以下
<item>
<A>xxxxxxxxxxxxxxxxxx</A>
<B>xxxxxxxxxxxxxxxxxxxx</B>
<C>xxxxxxxxxxxxxxxxxxxx</C>
<D>xxxxxxxxxxxxxxxxxxxxx</D>
</item>
<item>
<item>
<A>rrrrrrrrrrrrrrrrrrrrrrrrrrrrrrr</A>
<B>rrrrrrrrrrrrrrrrrrrrrr</B>
<C>rrrrrrrrrrrrrrrrrrrrrr</C>
<D>rrrrrrrrrrrrrr</D>
</item>
<item>
<item>
<A>rrrrrrrrrrrrrrrrrrrrrrrrrrrrrrr</A>
<B>rrrrrrrrrrrrrrrrrrrrrr</B>
<C>rrrrrrrrrrrrrrrrrrrrrr</C>
<D>rrrrrrrrrrrrrr</D>
<E>rrrrrrrrrrrrrr</E>
</item>
<item>
x和r表示每个特定元素的数据。
以下是我的代码摘录, 我使用下面的代码将每个节点的每个元素添加到一个arraylist中,a,b,c,d是arraylists:
for (int i = 0; i < list.getLength(); i++) {
Element element = (Element)list.item(i);
String nodeName = element.getNodeName();
switch (nodeName) {
case "A":
a.add(element.getChildNodes().item(0).getNodeValue());
break;
case "B":
b.add(element.getChildNodes().item(0).getNodeValue());
break;
case "C":
c.add(element.getChildNodes().item(0).getNodeValue());
break;
case "D":
d.add(element.getChildNodes().item(0).getNodeValue());
break;
case "E":
e.add(element.getChildNodes().item(0).getNodeValue());
break;
问题在于XML结构将节点E添加到XML中的重复列表中的结构中。这会引起问题,因为我的arraylists的长度现在长度不同。在比较arraylists或创建arraylists表时,由于长度不同,数据不对齐。我能做什么才能使所有的arraylists都长度相同。我希望这是一个arraylist。
答案 0 :(得分:4)
同步列表似乎不是一个好习惯。如果您希望所有列表的大小相同,那么从概念上讲,您希望只有一个列表。因此,重新设计您的代码以符合正确的概念:
而不是几个bean列表:
List<A> a;
List<B> b;
List<C> c;
...
...为什么不用一个复合bean列表替换它:
class MyComposite
{
private A a;
private B b;
private C c;
public A getA()
{
return this.a;
}
public void setA(A a)
{
this.a=a;
}
// ... rest of getters and setters...
}
List<MyComposite> list;
因此,人口算法将是这样的:
// Iterate over the "item" nodes of the document:
private List<MyComposite> populate(Document doc)
{
NodeList items=doc.getElementsByTagName("item");
List<MyComposite> list=new ArrayList<MyComposite>(items.getLength());
for (int i = 0; i < items.getLength(); i++)
{
Element item = (Element)items.item(i);
MyComposite myComposite=parseItem(item);
list.add(myComposite);
}
return list;
}
// Create one MyComposite bean reading the child nodes of an input "item" node:
private MyComposite parseItem(Element item)
{
MyComposite myComposite=new MyComposite();
NodeList childNodes=item.getChildNodes();
for (int i = 0; i < childNodes.getLength(); i++)
{
// Processing some element in the form: <name>value</name>
Element element = (Element)childNodes.item(i);
String nodeName = element.getNodeName();
String nodeValue = element.getTextContent();
// Decide where to store the node value (in myComposite) depending on the node name:
switch (nodeName)
{
case "A":
myComposite.setA(nodeValue);
break;
case "B":
myComposite.setB(nodeValue);
break;
...
default: // An unknown node was found.
System.err.println("Warning: Node '"+nodeName+"' not recognized and will be ignored");
}
}
return myComposite;
}
通过这种方式,您可以将XML加载到一致的数据模型中,而不会有不同大小的列表。
答案 1 :(得分:0)
如果找不到具有该名称的节点,则在相应列表中添加dummy或null值。这将使所有的arraylist长度相等。
答案 2 :(得分:0)
假设你的“行动”的最后阶段,如“比较arraylists或创建arraylists的表格,数据由于长度不同而未对齐”所暗示的,是将数据存储到数据库中答案很简单.. 批量准备声明..这些美女非常适合做大量重复性的工作。 只需创建5(n)预备语句并根据需要添加批处理,给出元素的名称,元素的值和父键(例如相关项元素的“id”)并添加“准备好”插入相关准备好的声明的批次..比执行整个批次,你有它,同时免费照顾... 一个示例代码,我将如何设想这个(很长,但也许它会给你一些想法..)...在样本中所有准备好的语句做同样的事情,但我给了四个不同的“演员”方法,这样您就可以基本上为项目类型的每个不同“元素”自定义目标查询。另外,你应该计划一个完整的回滚方法,就像这个“东西”你将在达到queryLimit(10000)的上限时提交每个块(preparedstatement),所以为了回滚你需要做一个手动方法来清理相关的项目(例如,添加例如xml的“referral”id,它发起了自己的元素)。
public class ExternalQueryInputAnnex {
private int queryLimit = 10000;
//prep statement for elementA
private PreparedStatement ps1;
private int cnt1 = 0;
//prep statement for elementB
private PreparedStatement ps2;
private int cnt2 = 0;
//prep statement for elementC
private PreparedStatement ps3;
private int cnt3 = 0;
//prep statement for elementD
private PreparedStatement ps4;
private int cnt4 = 0;
//prep statement for elementE
private PreparedStatement ps5;
private int cnt5 = 0;
private void theThingYouNeed(List<Object> itemList)
{
for (int i = 0; i < list.getLength(); i++) {
Element element = (Element)list.item(i);
String nodeName = element.getNodeName();
switch (nodeName) {
case "A":
doPreparedStatementOne("element.getChildNodes().item(0).getNodeValue()", "A", "whatever");
break;
case "B":
doPreparedStatementTwo("element.getChildNodes().item(0).getNodeValue()", "B", "whatever");
break;
case "C":
doPreparedStatementThree("element.getChildNodes().item(0).getNodeValue()", "C", "whatever");
break;
case "D":
doPreparedStatementFour("element.getChildNodes().item(0).getNodeValue()", "D", "whatever");
break;
case "E":
//e.add(element.getChildNodes().item(0).getNodeValue());
doPreparedStatementFive("element.getChildNodes().item(0).getNodeValue()", "E", "whatever");
break;
}
}
}
private void doPreparedStatementFive(String attribute, String sonId, String fatherId) throws DatabaseException {
int i = 0;
String query = "INSERT INTO TRS_ORDER_PRICE_INT_DTL_TIMES "
+ "(SON_VALUE,SON_ID,FATHER_ID) "
+ "VALUES "
+ "(?,?,?)";
try {
if (ps5 == null)
{
ps5 = connect.prepareStatement(query);
}
ps5.setString(1, attribute);
ps5.setString(2, sonId);
ps5.setString(3, fatherId);
ps5.addBatch();
cnt5++;
if (cnt5 >= queryLimit)
{
ps5 = wrapperDoBulkQueryList(ps5, query);
cnt5 = 0;
}
}
} catch (SQLException e) {
logger.error("Error insertOrderPriceIntDtlTimes: "+e.getLocalizedMessage());
throw new DatabaseException("Sql Exception during insertOrderPriceIntDtlTimes: "+e.getLocalizedMessage());
}
}
private void doPreparedStatementFour(String attribute, String sonId, String fatherId) throws DatabaseException {
int i = 0;
String query = "INSERT INTO TRS_ORDER_PRICE_INT_DTL_TIMES "
+ "(SON_VALUE,SON_ID,FATHER_ID) "
+ "VALUES "
+ "(?,?,?)";
try {
if (ps4 == null)
{
ps4 = connect.prepareStatement(query);
}
ps4.setString(1, attribute);
ps4.setString(2, sonId);
ps4.setString(3, fatherId);
ps4.addBatch();
cnt4++;
if (cnt4 >= queryLimit)
{
ps4 = wrapperDoBulkQueryList(ps4, query);
cnt4 = 0;
}
}
} catch (SQLException e) {
logger.error("Error insertOrderPriceIntDtlTimes: "+e.getLocalizedMessage());
throw new DatabaseException("Sql Exception during insertOrderPriceIntDtlTimes: "+e.getLocalizedMessage());
}
}
private void doPreparedStatementThree(String attribute, String sonId, String fatherId) throws DatabaseException {
int i = 0;
String query = "INSERT INTO TRS_ORDER_PRICE_INT_DTL_TIMES "
+ "(SON_VALUE,SON_ID,FATHER_ID) "
+ "VALUES "
+ "(?,?,?)";
try {
if (ps3 == null)
{
ps3 = connect.prepareStatement(query);
}
ps3.setString(1, attribute);
ps3.setString(2, sonId);
ps3.setString(3, fatherId);
ps3.addBatch();
cnt3++;
if (cnt3 >= queryLimit)
{
ps3 = wrapperDoBulkQueryList(ps3, query);
cnt3 = 0;
}
}
} catch (SQLException e) {
logger.error("Error insertOrderPriceIntDtlTimes: "+e.getLocalizedMessage());
throw new DatabaseException("Sql Exception during insertOrderPriceIntDtlTimes: "+e.getLocalizedMessage());
}
}
private void doPreparedStatementTwo(String attribute, String sonId, String fatherId) throws DatabaseException {
int i = 0;
String query = "INSERT INTO TRS_ORDER_PRICE_INT_DTL_TIMES "
+ "(SON_VALUE,SON_ID,FATHER_ID) "
+ "VALUES "
+ "(?,?,?)";
try {
if (ps2 == null)
{
ps2 = connect.prepareStatement(query);
}
ps2.setString(1, attribute);
ps2.setString(2, sonId);
ps2.setString(3, fatherId);
ps2.addBatch();
cnt2++;
if (cnt2 >= queryLimit)
{
ps2 = wrapperDoBulkQueryList(ps2, query);
cnt2 = 0;
}
}
} catch (SQLException e) {
logger.error("Error insertOrderPriceIntDtlTimes: "+e.getLocalizedMessage());
throw new DatabaseException("Sql Exception during insertOrderPriceIntDtlTimes: "+e.getLocalizedMessage());
}
}
private void doPreparedStatementOne(String attribute, String sonId, String fatherId) throws DatabaseException {
int i = 0;
String query = "INSERT INTO TRS_ORDER_PRICE_INT_DTL_TIMES "
+ "(SON_VALUE,SON_ID,FATHER_ID) "
+ "VALUES "
+ "(?,?,?)";
try {
if (ps1 == null)
{
ps1 = connect.prepareStatement(query);
}
ps1.setString(1, attribute);
ps1.setString(2, sonId);
ps1.setString(3, fatherId);
ps1.addBatch();
cnt1++;
if (cnt1 >= queryLimit)
{
ps1 = wrapperDoBulkQueryList(ps1, query);
cnt1 = 0;
}
}
} catch (SQLException e) {
logger.error("Error insertOrderPriceIntDtlTimes: "+e.getLocalizedMessage());
throw new DatabaseException("Sql Exception during insertOrderPriceIntDtlTimes: "+e.getLocalizedMessage());
}
}
// do any sub-querylimit execution
public void cleanUpExecution() throws DatabaseException
{
if (ps1 != null)
{
logger.debug("ps1");
wrapperDoBulkQueryList(ps1, null);
}
if (ps2 != null)
{
logger.debug("ps2");
wrapperDoBulkQueryList(ps2, null);
}
if (ps3 != null)
{
logger.debug("ps3");
wrapperDoBulkQueryList(ps3, null);
}
if (ps4 != null)
{
logger.debug("ps4");
wrapperDoBulkQueryList(ps4, null);
}
if (ps5 != null)
{
logger.debug("ps5");
wrapperDoBulkQueryList(ps5, null);
}
}
public PreparedStatement wrapperDoBulkQueryList(PreparedStatement queryBulk, String query) throws DatabaseException
{
queryBulk = wrapperDoBulkQueryListDirect(queryBulk, null, query);
return queryBulk;
}
public PreparedStatement wrapperDoBulkQueryListDirect(PreparedStatement queryList, Long load_id, String query) throws DatabaseException
{
if (doBulkQueryList(queryList))
{
if (query != null)
{
try
{
queryList = connect.prepareStatement(query);
return queryList;
}
catch (SQLException e)
{
throw new DatabaseException("Exception of sqlexception while regenerating statement:"+e.getLocalizedMessage());
}
}
else
{
logger.debug("Query not passed, cleanup for preparedstatement");
//System.out.println("Query not passed, cleanup for preparedstatement");
return queryList;
}
}
else
{
// do delete based on loadid
// then throw exception
throw new DatabaseException("Some failure");
}
}
public boolean doBulkQueryList(PreparedStatement queryList) throws DatabaseException
{
// do bulk query execution
try {
connect.setAutoCommit(false);
//System.out.println("query: "+singleQuery.toString());
long startSetup = System.currentTimeMillis();
int[] results = queryList.executeBatch();
long finishSetup = (System.currentTimeMillis()-startSetup)/1000;
if(finishSetup > 5){
logger.warn("Execution "+results.length+" insert in "+finishSetup+" seconds.");
}
for(int singleResult : results){
if (singleResult >= 0) {
// System.out.println("OK; updateCount");
}
else if (singleResult == Statement.SUCCESS_NO_INFO) {
// System.out.println("OK; insert=Statement.SUCCESS_NO_INFO");
}
else if (singleResult == Statement.EXECUTE_FAILED) {
System.out.println("Failure; updateCount=Statement.EXECUTE_FAILED");
}
}
insertedRows = insertedRows + results.length;
//System.out.println("Query effettuata");
connect.commit();
} catch (SQLException e) {
//e.printStackTrace();
if (connect != null) {
try {
logger.error("Transaction is being rolled back: ",e);
connect.rollback();
return false;
} catch(SQLException excep) {
throw new DatabaseException("Error Transaction commit");
}
}
}
finally{
if (queryList != null) {
try {
queryList.close();
} catch (SQLException e) {
logger.error("Transaction is being rolled back: "+e.getLocalizedMessage());
}
}
try {
connect.setAutoCommit(true);
} catch (SQLException e) {
logger.error("Set true auto commit: ",e);
}
}
return true;
}
}
答案 3 :(得分:0)
如果你的xml是正确的root标签,最简单的方法是使用Jaxb。由于JDK 1.6 JaxB开箱即用。代码简短而简单,如
File file = new File("Item.xml");
DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
JAXBContext jaxbContext = JAXBContext.newInstance(Items.class);
Unmarshaller jaxbUnmarshaller = jaxbContext.createUnmarshaller();
Items items = (Items) jaxbUnmarshaller.unmarshal(dBuilder.parse(file));
一个完整的例子。说你的xml就像
<items>
<item>
<A>xxxxxxxxxxxxxxxxxx</A>
<B>xxxxxxxxxxxxxxxxxxxx</B>
<C>xxxxxxxxxxxxxxxxxxxx</C>
<D>xxxxxxxxxxxxxxxxxxxxx</D>
</item>
<item>
<A>rrrrrrrrrrrrrrrrrrrrrrrrrrrrrrr</A>
<B>rrrrrrrrrrrrrrrrrrrrrr</B>
<C>rrrrrrrrrrrrrrrrrrrrrr</C>
<D>rrrrrrrrrrrrrr</D>
</item>
<item>
<A>rrrrrrrrrrrrrrrrrrrrrrrrrrrrrrr</A>
<B>rrrrrrrrrrrrrrrrrrrrrr</B>
<C>rrrrrrrrrrrrrrrrrrrrrr</C>
<D>rrrrrrrrrrrrrr</D>
<E>rrrrrrrrrrrrrr</E>
</item>
</items>
然后你需要创建2个一级父Items
和孩子Item
(或任何你喜欢的名字)。
import java.io.File;
import java.io.Serializable;
import java.util.List;
import javax.xml.bind.JAXBContext;
import javax.xml.bind.Unmarshaller;
import javax.xml.bind.annotation.XmlElement;
import javax.xml.bind.annotation.XmlRootElement;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
@XmlRootElement(name = "items")
class Items implements Serializable {
List<Item> item;
public List<Item> getItem() {
return item;
}
@XmlElement(name = "item")
public void setItem(List<Item> item) {
this.item = item;
}
@Override
public String toString() {
return "Items [" + item + "]";
}
}
class Item implements Serializable {
private String a;
private String b;
private String c;
private String d;
private String e;
public String getA() {
return a;
}
@XmlElement(name = "A")
public void setA(String a) {
this.a = a;
}
public String getB() {
return b;
}
@XmlElement(name = "B")
public void setB(String b) {
this.b = b;
}
public String getC() {
return c;
}
@XmlElement(name = "C")
public void setC(String c) {
this.c = c;
}
public String getD() {
return d;
}
@XmlElement(name = "D")
public void setD(String d) {
this.d = d;
}
public String getE() {
return e;
}
@XmlElement(name = "E")
public void setE(String e) {
this.e = e;
}
@Override
public String toString() {
return "Item [a=" + a + ", b=" + b + ", c=" + c + ", d=" + d + ", e="
+ e + "]";
}
}
public class ItemParser {
public static void main(String[] args) throws Exception {
File file = new File("Item.xml"); // Give appropriate file path.
DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
JAXBContext jaxbContext = JAXBContext.newInstance(Items.class);
Unmarshaller jaxbUnmarshaller = jaxbContext.createUnmarshaller();
Items items = (Items) jaxbUnmarshaller.unmarshal(dBuilder.parse(file));
System.out.println(items);
}
}