Android 中 String、StringBuffer 和 StringBuilder 的内存不足异常
我在将 1.8MB 图像转换为字节然后加密,最后转换为字符串(日志中打印的长度为 1652328)时遇到内存不足异常。然后,我将此字符串附加到某种 XML 格式中以进行发布,这正是真正的问题出现的地方。使用 StringBuffer
或 StringBuilder
向此 pictureString 附加一些标签或添加到字符串时,发生内存不足异常。我该如何解决这个问题?
对于小图像,此问题不会重现。
下面的代码将路径 path
处的图片转换为 String
。
fis = new FileInputStream(path);
buffer = new byte[fis.available()];
try {
fis.read(buffer, 0, buffer.length);
String byteString =
com.mobile.android.components.Base64.encodeBytes(buffer);
return byteString;
} catch (IOException ex) {
}
上面的 byteString
被附加到 xml post 中,如下所示。
StringBuilder pictureName = new StringBuilder();
pictureName.append(byteString ); //here array out of bound at StringBuilder.extendBuffer
..........
appending continues
更新
在上面的附加中,编码的byteStream
使用cypher AES加密,然后附加到StringBuilder
。
I'm facing an Out of Memory Exception while converting a 1.8MB image to bytes and then encrypt, finally converting into a string (length printed in log is 1652328). And then, I'm appending this string to some XML format to post, where the real problem arises. While appending some tags to this pictureString using StringBuffer
or StringBuilder
or adding to a string Out of Memory exception is occuring. How can I resolve this issue?
For small images this issue is not replicating.
The below piece of code converts a picture at path path
to String
.
fis = new FileInputStream(path);
buffer = new byte[fis.available()];
try {
fis.read(buffer, 0, buffer.length);
String byteString =
com.mobile.android.components.Base64.encodeBytes(buffer);
return byteString;
} catch (IOException ex) {
}
The above byteString
is appended to xml post as follows.
StringBuilder pictureName = new StringBuilder();
pictureName.append(byteString ); //here array out of bound at StringBuilder.extendBuffer
..........
appending continues
UPDATED
In the above appending, encoded byteStream
is encrypted using cypher AES and then appended to StringBuilder
.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
将位图转换为字节数组后,立即调用
bitmap.recycle();
。这将释放与该位图关联的本机对象,并清除对像素数据的引用。更新
很明显,从文件流读取的内存块太大而无法处理。避免一次读取整个文件。一点一点地做。将字符串附加到 xml,而不使用中间字符串对象。
更新 2
您可以执行类似的操作,以避免在将其发送到服务器时加载整个 xml 文件。
然后写入边界字符,刷新并关闭流。
Call
bitmap.recycle();
as soon as you have converted the bitmap to a byte array. This will free the native object associated with this bitmap, and clear the reference to the pixel data.Update
Its obvious that the memory chunk read from the filestream is too large to handle. Avoid reading the whole file at once. Do it piece by piece. Append the string to the xml without using an intermediate string object.
Update 2
You could do something like this to avoid loading the whole xml file while sending it to server.
Then write the boundry characters, flush and close the streams.
感谢大家的支持。
我终于利用文件操作最大限度地优化了我的代码。
对于编码,我使用
Base64.encodeFileToFile(picturePath,encodedPicturePath);
我将编码后的图像保存在文件中。
然后对于加密,我使用
CypherOutPutStream
,其中 FileOutputStream 在构造函数中传递。因此加密也是使用文件完成的。最后一步是在使用 HttpPost 时,我曾经将全部加密数据作为
StringEntity
发送,这是OutOfMemeoryException
的最终障碍。我将 StringEntity 更改为FileEntity< /code>。这减少了我的应用程序的堆消耗,从而提高了整体性能和上传能力。
笔记:
不要以块的形式对编码图像进行加密,这会改变整个编码数据。请在单个块中进行加密。
失败:
在我使用文件进行编码之前,我将整个图片分块并编码到一个文件中。但是,如果我解码编码文件,我无法获得原始图片。
问候,沙
Thanks everyone for the support.
I finally optimized my code to a max extent using file operations.
For encoding I used
Base64.encodeFileToFile(picturePath, encodedPicturePath);
I saved the encoded image in a file.
And then for encryption,I used
CypherOutPutStream
where a FileOutputStream is passed in constructor.So Encryption is also done using file.The final step is while using HttpPost,I used to send the total encrypted data as a
StringEntity
which is final Hurdle forOutOfMemeoryException
.I changed the StringEntity toFileEntity
.This reduced the heap consumption of my application and thus improved the overall performance and upload capacity.Note:
Dont Encrypt the encoded image in chunks which will change the overall encoded data.Do it inn a single piece.
Failures:
Before i used files for Encoding ,I chunked the whole picture and encoded to a file.But,If i decode the encoded file,I failed to get the original picture.
Regards,Sha