检测流中不可映射的字符

时间:2016-07-13 06:57:23

标签: java

我正在用单字节编码将字符流写入文本文件。 我希望能够检测流中不可映射的字符以采取后备操作(这是高级别的,不会删除或替换无效字符)。

我现在正在使用OutputStreamWriter,但我怎么能确定它会导致映射失败?

private void convert(Iterable<String> lines, OutputStream os) throws CoreException, IOException {
    String lineDelimiter = ResourcesUtils.getLineDelimiter(file.getProject());
    Charset charset = Charset.forName(file.getCharset());
    CharsetEncoder encoder = charset.newEncoder();
    encoder.onUnmappableCharacter(CodingErrorAction.REPORT);
    try (OutputStreamWriter writer = new OutputStreamWriter(os, encoder)) {
        Joiner.on(lineDelimiter).appendTo(writer, lines);
    }
}

此代码抛出示例无效输入,但不清楚是否可以保证在OutputStreamWriter或输入的其他实现上执行此操作。

使用不可映射的字符转换流时获取异常的有效方法是什么?

1 个答案:

答案 0 :(得分:0)

我尝试使用各种构造函数构造OutputStreamWriter,并测试它是否会在写入尝试时抛出无法输入的输入。

通用测试用例看起来像:

ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
Writer writer = createWriter(outputStream);
writer.write("ホク");
writer.close();

使用以下createWriter()实现:

  • new OutputStreamWriter(outputStream, "windows-1251") - 不投掷
  • new OutputStreamWriter(outputStream, Charset.forName("windows-1251")) - 不投掷
  • 配置编码器:

    CharsetEncoder encoder = Charset.forName(“windows-1251”)。newEncoder(); encoder.onUnmappableCharacter(CodingErrorAction.IGNORE); new OutputStreamWriter(outputStream,encoder);

    不抛出

  • new OutputStreamWriter(outputStream, Charset.forName("windows-1251").newEncoder()) - 确实会抛出

这种行为有点令人惊讶is not specified。 此外,文件说:

  

此类始终替换格式错误的代理元素且无法映射   具有charset默认替换序列的字符序列。   当更多地控制时,应该使用CharsetEncoder类   编码过程是必需的。

这与上一次实验结果相矛盾。

在Java(TM)SE运行时环境(build 1.8.0_72-b15)(linux)上测试

OutputStreamWriter一般不会抛出映射失败,但有时会这样做。我仍然会使用它,因为原始的CharsetEncoder API不适合流,但欢迎使用更强大的解决方案。