流式传输时缓冲区字节数组如何连续填充?
下面的代码用于读取Files
int bytesRead; byte[] bytes = new byte[1000]; //buffer FileInputStream fis = new FileInputStream(uploadedFile); while ((bytesRead = fis.read(bytes)) != -1) { fis.read(bytes, 0, bytesRead); } fis.close();
根据read()方法的api
将此输入流中的b.length个字节数据读入一个字节数组。 此方法将阻塞,直到某些输入可用。
没有指定它重新填充bytes
数组,但是流填充array
直到file
成功read.
。
但内部如何保持这种魔力?
我看过源代码或读取方法
public int More ...read(byte b[]) throws IOException { 214 return readBytes(b, 0, b.length); 215 }
和readBytes
的源代码是
200 private native int More ...readBytes (byte b[], int off, int len) throws IOException;
有提到如何bytes
..
我上传了一个500MB的文件没有任何问题,分配1000
字节array
。
如果您问为什么可以读取大约1 KB缓冲区的~500 MB文件,那是因为每次进行循环时都会覆盖缓冲区的内容(大约500,000次)。
如果您正在询问如何实际实现读取函数,请注意底层调用包含关键字native
。 这意味着通过JNI调用本机代码。 确切的实现将依赖于JVM和OS。
Michael Schaeffer发表了一篇关于readBytes
的精彩文章
简而言之:
Java中的文件I / O是通过读入本地缓冲区,然后从本地缓冲区复制到最初传入int read(byte byf [])的Java byte []来实现的。 这种双重复制很慢,但如果读取缓冲区大于8K,则还需要堆分配第二个读取缓冲区。
还有许多其他有用的细节,但它更容易阅读。
- 将数组php转换为java
- 在数组上调用.length与保存大小变量的性能是否存在差异?
- 运行Tomcat服务器org.apache.catalina.deploy.WebXml addServlet时出现exception
- ECEF到lla(lat,lon,alt)在java中
- 使用HashBasedTable作为累加器的Guava ImmutableTable的Java 8收集器给出了IllegalAccessError
- Lucene:如何在几个独立的索引集上执行搜索并合并结果?
- 使用java中的regex在两个特定单词之间提取子字符串
- MigLayout:相对于屏幕大小调整组件大小
- 如何将sql DATE映射到LocalDate