给定一个以毫秒为单位的时间,我们可以使用以下代码片段创建XMLGregorianCalendar。
GregorianCalendar greCal = new GregorianCalendar();
greCal.setTimeInMillis(timeInMilliseconds);
XMLGregorianCalendar xmlCal = DatatypeFactory.newInstance().newXMLGregorianCalendar(greCal));
但问题是,它严重影响了性能。
http://www.java.net/node/666491
有一个与SUN提交的错误,但他们没有列出任何变通方法。 http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=6466177
尝试寻找其他替代方案,但徒劳无功。你们中的任何一个人都有其他方法可以做同样的事吗?
由于
拉曼
答案 0 :(得分:12)
昂贵的部分是DatatypeFactory.newInstance(),它在分析应用程序时显示在右上方。 在我们的例子中,我们将DatatypeFactory存储为静态变量,并且我们能够绕过重复的初始化。这应该工作,因为我们使用的DatatypeFactory实现应该是线程安全的(如错误报告中所述)。我同意这可能会根据所使用的实施方式而改变。所以我建议再次检查。
private static DatatypeFactory datatypeFactory;
static{
try {
datatypeFactory = DatatypeFactory.newInstance();
} catch (DatatypeConfigurationException e) {
throw new RuntimeException("Init Error!", e);
}
}
public void foo(long timeInMilliseconds){
GregorianCalendar greCal = new GregorianCalendar(); greCal.setTimeInMillis(timeInMilliseconds);
XMLGregorianCalendar xmlGregorienCalendar = datatypeFactory.newXMLGregorianCalendar(greCal);
// ...
}
答案 1 :(得分:9)
由于@VivaceVivo提到DataFactory.newInstance()是昂贵的并且impl不保证是线程安全的,考虑使用ThreadLocal:
final private static ThreadLocal<DatatypeFactory> datatypeFactoryHolder = new ThreadLocal<DatatypeFactory>()
{
@Override
protected DatatypeFactory initialValue()
{
try
{
return DatatypeFactory.newInstance();
} catch (DatatypeConfigurationException e)
{
throw new IllegalStateException("failed to create " + DatatypeFactory.class.getSimpleName(), e);
}
}
};
public static XMLGregorianCalendar dateToXMLGregorianCalendar(Date date)
{
GregorianCalendar c = new GregorianCalendar();
c.setTime(date);
return datatypeFactoryHolder.get().newXMLGregorianCalendar(c);
}
}
..只要你不关心线程是否保留额外的对象或者有必要在需要时清除ThreadLocalMap