我得到了XML和架构文件。我的目标是从XML输出所有数据(没有重复项),并在出生日期之前对该列表进行排序。目前,我已打印出所有数据(重复),而且我不知道下一步该怎么做。我尝试了不同的方法,但未成功。
最佳答案
编辑
再次阅读该帖子后,我意识到我也需要删除公仔,所以:
您可以使用TreeSet
施加歧义,并按DOB排序-我假设姓,名和出生日期相同的人就是同一个人。
首先,我将您的Node包装在一个实现Comparable
的类中,该类还将获取您拥有的所有这些属性。包装程序需要实现Comparable
,因为TreeSet
使用此方法来确定元素是否不同(a.compareTo(b) != 0
)以及如何对其进行排序。
public static final class NodeWrapper implements Comparable<NodeWrapper> {
private static final SimpleDateFormat DOB_FORMAT = new SimpleDateFormat("yyyy-MM-dd");
private final Element element;
private final Date dob;
private final String firstName;
private final String surName;
private final String sex;
public NodeWrapper(final Node node) {
this.element = (Element) node;
try {
this.dob = DOB_FORMAT.parse(initDateOfBirth());
} catch (ParseException ex) {
throw new RuntimeException("Failed to parse dob", ex);
}
this.firstName = initFirstName();
this.surName = initSurnameName();
this.sex = initSex();
}
private String initFirstName() {
return getNodeValue("firstname");
}
private String initSurnameName() {
return getNodeValue("surname");
}
private String initDateOfBirth() {
return getNodeValue("dateofbirth");
}
private String initSex() {
return getNodeValue("sex");
}
private String getNodeValue(final String name) {
return element.getElementsByTagName(name).item(0).getTextContent();
}
public Node getNode() {
return element;
}
Date getDob() {
return dob;
}
public String getFirstName() {
return firstName;
}
public String getSurName() {
return surName;
}
public String getDateOfBirth() {
return DOB_FORMAT.format(dob);
}
public String getSex() {
return sex;
}
public int compareTo(NodeWrapper o) {
int c;
c = getDob().compareTo(o.getDob());
if (c != 0) {
return c;
}
c = getSurName().compareTo(o.getSurName());
if (c != 0) {
return c;
}
return getFirstName().compareTo(o.getFirstName());
}
@Override
public int hashCode() {
int hash = 5;
hash = 47 * hash + (this.dob != null ? this.dob.hashCode() : 0);
hash = 47 * hash + (this.firstName != null ? this.firstName.hashCode() : 0);
hash = 47 * hash + (this.surName != null ? this.surName.hashCode() : 0);
return hash;
}
@Override
public boolean equals(Object obj) {
if (obj == null) {
return false;
}
if (getClass() != obj.getClass()) {
return false;
}
final NodeWrapper other = (NodeWrapper) obj;
if (this.dob != other.dob && (this.dob == null || !this.dob.equals(other.dob))) {
return false;
}
if ((this.firstName == null) ? (other.firstName != null) : !this.firstName.equals(other.firstName)) {
return false;
}
if ((this.surName == null) ? (other.surName != null) : !this.surName.equals(other.surName)) {
return false;
}
return true;
}
@Override
public String toString() {
return "FirstName: " + getFirstName() + ". Surname: " + getSurName() + ". DOB: " + getDateOfBirth() + ". Sex: " + getSex() + ".";
}
}
因此,如果出生日期,姓氏和名字都相等,我们假定它是同一个人-我们返回0。这是一种好习惯,如果以这种方式使用
compareTo
使其与equals一致,则如果a.compareTo(b)==0
然后a.equals(b)
,我还添加了必需的equals
和hashCode
方法。现在,您可以在代码中使用
TreeSet
,该代码将自动排序并保证不合时宜:final Document doc = DocumentBuilderFactory.newInstance().newDocumentBuilder().parse(new File("file.xml"));
final Set<NodeWrapper> inimesteList = new TreeSet<NodeWrapper>();
final NodeList isa = doc.getElementsByTagName("isa");
for (int i = 0; i < isa.getLength(); i++) {
inimesteList.add(new NodeWrapper(isa.item(i)));
}
final NodeList ema = doc.getElementsByTagName("ema");
for (int i = 0; i < ema.getLength(); i++) {
inimesteList.add(new NodeWrapper(ema.item(i)));
}
final NodeList isik = doc.getElementsByTagName("isik");
for (int i = 0; i < isik.getLength(); i++) {
inimesteList.add(new NodeWrapper(isik.item(i)));
}
System.out.println();
System.out.println("Total: " + inimesteList.size());
for (final NodeWrapper nw : inimesteList) {
System.out.println(nw);
}
我还添加了一个
toString
方法,并使用它来打印节点-这使代码更简洁。Document
方法虽然看起来比JAXB更简单,但是却充满了这种乏味。由于您已经有了一个架构,因此我强烈建议您取消对xjc
和JAXB的编组,这将使这类事情变得更加容易。