xstream - 以UTF-8保存XML的正确方法

时间:2010-09-04 15:15:34

标签: java xml xstream

以前,通过xstream以UTF-8编码读取 XML,我使用的是DomDriver:

XStream xStream = new XStream(new DomDriver("UTF-8"));

然而,后来我意识到这非常慢。我使用以下方式:

Optimize loading speed of xstream

这至少可以正常工作。

但是,后来,我意识到同样的技术不能应用于编写XML。我会得到所有???字符。

这是在

期间使用DomDriver的最后一个可行代码
public static boolean toXML(Object object, File file) {
    XStream xStream = new XStream(new DomDriver("UTF-8"));
    OutputStream outputStream = null;

    try {
        outputStream = new FileOutputStream(file);
        xStream.toXML(object, outputStream);
    }
    catch (Exception exp) {
        log.error(null, exp);
        return false;
    }
    finally {
        if (false == close(outputStream)) {
            return false;
        }
        outputStream = null;
    }

    return true;
}

上面的代码工作正常。为了与不使用DomDriver的读取方法匹配,我将代码更改为

public static boolean toXML(Object object, File file) {
    XStream xStream = new XStream();
    OutputStream outputStream = null;
    Writer writer = null;

    try {
        outputStream = new FileOutputStream(file);
        writer = new OutputStreamWriter(outputStream, Charset.forName("UTF-8"));
        xStream.toXML(object, outputStream);
    }
    catch (Exception exp) {
        log.error(null, exp);
        return false;
    }
    finally {
        if (false == close(writer)) {
            return false;
        }
        if (false == close(outputStream)) {
            return false;
        }
        writer = null;
        outputStream = null;
    }

    return true;
}

这一次,我所有的汉字都改为???

我可能知道我做错了什么吗?

1 个答案:

答案 0 :(得分:11)

看看这段代码:

outputStream = new FileOutputStream(file);
writer = new OutputStreamWriter(outputStream, Charset.forName("UTF-8"));
xStream.toXML(object, outputStream);

创建一个将使用UTF-8的作家 - 然后完全忽略它!

请改为尝试:

xStream.toXML(object, writer);

另外,作为一种风格问题,我建议您考虑以下事项:

  • 不要将结果与布尔常量进行比较;只需使用if (foo)if (!foo)代替
  • 抓住Exception 非常很少是一个好主意;抓住特定的例外
  • 返回一个布尔值来表示成功或失败不是惯用的Java;通常,如果某些事情失败,则例外情况会更好
  • 如果第一个close失败,您将在第二次close调用之前退出该方法,这可能不是您想要的。 (事实上​​,关闭OutputStreamWriter`无论如何都会关闭流,但要考虑事情的原理。)
  • 在方法结束时将局部变量设置为null是不必要的,并且会使代码混乱