【问题标题】:getResponseAsStream - What does the InputStream point to?getResponseAsStream - InputStream 指向什么?
【发布时间】:2018-06-15 10:01:43
【问题描述】:

我很好奇 getResponseAsStream for HttpClient 是如何工作的。

根据这个article,你应该使用getResponseAsStream而不是将整个响应加载到内存中。

我的问题是这是如何工作的,InputStream 指向哪里?

举一个例子,一个特定的 REST 服务请求返回一个生成的 JSON 服务器将其存储在哪里,以便可以将其流式传输到客户端?主内存是唯一的选择。

如果是这种情况,您并没有解决内存耗尽的问题。 这到底是如何工作的?

【问题讨论】:

    标签: java inputstream apache-httpclient-4.x


    【解决方案1】:

    考虑以下极其简化的场景:

    服务器生成大量数据,例如通过读取大文件。它通过 OutputStream 将数据写入发送缓冲区。网络堆栈从发送缓冲区读取数据并将数据包发送到客户端。这里传入的数据被放入接收缓冲区。

    最终接收缓冲区已满,客户端停止接受来自服务器的数据包。这会导致发送缓冲区被填满。此时服务器已暂停,因为它无法再将数据放入发送缓冲区。

    客户端使用getResponseAsStream 获取一个从接收缓冲区读取数据的 InputStream 实现。一旦客户端通过 InputStream 读取数据,接收缓冲区清空,客户端的网络堆栈再次接受数据包,这导致服务器端的发送缓冲区耗尽。现在服务器可以再次将数据写入缓冲区。

    这样,客户端可以读取任意数量的数据,并且系统永远不需要比发送和接收缓冲区更多的空间。

    当然,这是极其简化的。有更多的层,涉及更多的缓冲区。但我希望这能解释基本原理。

    【讨论】:

    • 所以 InputStream 实际上指向服务器上的那个缓冲区?假设我们过于简单化了。
    • @ng.newbie 是的,InputStream-Implementation 将引用接收缓冲区或类似的东西。
    • @ng.newbie 请记住,InputStream 只是一个接口,描述了一种让您可以按顺序读取字节的功能。字节的来源隐藏在实现中。
    • 所以使用 InputStream 的全部意义在于,我可以用相当小的缓冲区处理更多数据,对吧?否则将分配一个大缓冲区来保存整个输入。
    • @ng.newbie 这取决于您如何处理读取的每个字节。如果您将它存储在数组或其他东西中,那么是的,每个字节最终都存储在内存中。如果您将其打印到控制台,或将其写入文件,或将其写入某些其他输出流,那么不,所有内容都不会存储到内存中。就像您在电视上观看视频帧流一样:一旦显示一帧,它就会被丢弃并被下一帧替换。整个视频不需要存储在内存中。
    猜你喜欢
    • 1970-01-01
    • 2014-04-05
    • 2018-04-14
    • 2015-10-24
    • 2021-11-23
    • 2020-04-07
    • 2011-05-21
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多