Java InputStream读取字符串尾部会自动加0的问题
几年前写的一个从MHT(MIME)格式文件中读HTML的代码,大概代码如下:
InputStream hs = ((MimePart)part).getInputStream();
byte[] bts = new byte[hs.available()];
hs.read(bts);
tHtmlBody = new String(bts, "GBK");
一直用得挺好,但最近发现在某些服务器上读出来的HTML尾部居然会多加0,有时加一个0,有时加几十个0。但在开发的机器上一调试却又十分正常,真是奇怪。
于是开始写日志跟踪分析,最后发现问题出在available()上。出问题的MHT文件中的HTML代码采用了Quoted Printable编码,对应使用的解码类是QPDecoderStream,而继续分析这个QPDecoderStream类的available(),发现其实现代码有如下内容:
public int available() throws IOException {
// This is bogus ! We don't really know how much
// bytes are available *after* decoding
return in.available();
}
很显然,这个代码的作者已经告诉我们,这个available方法是直接返回了原始数据流的大小,而不是我们想像中的解码后的大小。例如原始的QP编码文件是100字节,解码后可能就只有90字节,因实际读出来的内容比available要小,从而导致获得的HTML内容后面填0。而之前我们很多情况下是不用QP编码的,所以没发现这个问题。
解决办法是不要信任available返回的大小,还是以read返回的字节数为准:
InputStream hs = ((MimePart)part).getInputStream();
int n=hs.available();
byte[] bts = new byte[n];
n=hs.read(bts,0,n);
tHtmlBody = new String(bts,0,n, "GBK");
修改代码后再运行,果然问题解决,不再加0了。
作者“huzgd的专栏”
补充:软件开发 , Java ,