如何提升Android设备中Writer的大文件写入速度?
优化大文件写入速度的解决方案
问题根源
你当前的代码逐个字节读取并逐个字符写入,这种单字节IO操作会触发大量底层系统调用,真实Android设备的存储IO延迟远高于模拟器,大文件场景下会导致写入速度急剧下降。另外,ISO-8859-1是单字节编码,字节与字符一一对应,完全没必要通过Writer中转,直接操作字节流效率更高。
方案1:直接使用OutputStream(最优解)
既然最终要写入的是字节数据,跳过Writer直接用OutputStream,配合缓冲流批量写入,能大幅减少IO调用次数:
String filePath = Display.getInstance().getDatabasePath("TestDB.db"); FileSystemStorage fss = FileSystemStorage.getInstance(); InputStream is = fss.openInputStream(filePath); byte[] plainBytes = Util.readInputStream(is); // 加密数据库文件内容 Log.p("Starting file encryption..."); byte[] cipherByteArray = FilesCipher.encryptFile(plainBytes); Log.p("Done encrypting file"); String encryptedFilePath = fss.getAppHomePath() + "EncryptedDB.db"; Log.p("Writing to new file started..."); try (OutputStream os = new BufferedOutputStream(fss.openOutputStream(encryptedFilePath))) { os.write(cipherByteArray); // 直接批量写入整个字节数组 Log.p("Done writing to a new file"); } catch (Exception e) { Log.p("Error " + e); }
如果担心大文件一次性读入内存导致OOM,可以改成流式加密+流式写入,分块处理:
String filePath = Display.getInstance().getDatabasePath("TestDB.db"); FileSystemStorage fss = FileSystemStorage.getInstance(); String encryptedFilePath = fss.getAppHomePath() + "EncryptedDB.db"; Log.p("Starting stream encryption and writing..."); try (InputStream is = new BufferedInputStream(fss.openInputStream(filePath)); OutputStream os = new BufferedOutputStream(fss.openOutputStream(encryptedFilePath))) { byte[] buffer = new byte[8192]; // 8KB缓冲区,可根据设备调整 int bytesRead; while ((bytesRead = is.read(buffer)) != -1) { byte[] encryptedChunk = FilesCipher.encryptChunk(buffer, 0, bytesRead); // 需要实现分块加密方法 os.write(encryptedChunk); } Log.p("Done writing to a new file"); } catch (Exception e) { Log.p("Error " + e); }
方案2:如果必须使用Writer
如果业务场景要求必须用Writer,一定要用BufferedWriter做缓冲,并且批量读写,避免单字符操作:
String filePath = Display.getInstance().getDatabasePath("TestDB.db"); FileSystemStorage fss = FileSystemStorage.getInstance(); InputStream is = fss.openInputStream(filePath); byte[] plainBytes = Util.readInputStream(is); Log.p("Starting file encryption..."); byte[] cipherByteArray = FilesCipher.encryptFile(plainBytes); Log.p("Done encrypting file"); ByteArrayInputStream byteArrayInputStream = new ByteArrayInputStream(cipherByteArray); String encryptedFilePath = fss.getAppHomePath() + "EncryptedDB.db"; Log.p("Writing to new file started..."); try (Writer w = new BufferedWriter(new OutputStreamWriter(fss.openOutputStream(encryptedFilePath), "ISO-8859-1"))) { char[] buffer = new char[8192]; int charsRead; while ((charsRead = byteArrayInputStream.read(buffer)) != -1) { w.write(buffer, 0, charsRead); // 批量写入字符数组 } Log.p("Done writing to a new file"); } catch (Exception e) { Log.p("Error " + e); }
关键优化点
- 缓冲流:
BufferedInputStream/BufferedOutputStream/BufferedWriter会先将数据缓存到内存,积累到一定量再触发一次底层IO操作,大幅减少系统调用次数。 - 批量操作:避免单字节/单字符的读写,改用数组批量处理,这是提升IO性能的核心。
- 流式处理:对于超大文件,不要一次性加载到内存,分块读写能避免内存溢出,同时保持高效。
内容的提问来源于stack exchange,提问作者Eric
相关产品推荐
相关产品推荐

