Java 使用InputStreamReader和BufferedReader缓慢读取HTTP响应?

Java 使用InputStreamReader和BufferedReader缓慢读取HTTP响应?,java,http,httpurlconnection,stringbuilder,inputstreamreader,Java,Http,Httpurlconnection,Stringbuilder,Inputstreamreader,我有以下Java代码向web服务器发送HTTP请求并读取响应: StringBuilder response = new StringBuilder(50000); URL url2 = new URL(ServiceURL); connection = (HttpURLConnection)url2.openConnection(); connection.setRequestMethod("POST"); //... (some more connection settings) ...

我有以下Java代码向web服务器发送HTTP请求并读取响应:

StringBuilder response = new StringBuilder(50000);
URL url2 = new URL(ServiceURL); 
connection = (HttpURLConnection)url2.openConnection();
connection.setRequestMethod("POST");

//... (some more connection settings) ...

BufferedWriter  wr = new BufferedWriter(new OutputStreamWriter(connection.getOutputStream(), "UTF-8"));

wr.write(Request);
wr.flush ();
wr.close ();

InputStream is = connection.getInputStream();       
BufferedReader rd = new BufferedReader(new InputStreamReader(is));

int i = 0;
while ((i = rd.read()) > 0) {
    response.append((char)i);
}
它适用于大多数情况,但有一台服务器返回相当大的XML(大约500KB;我想这对于一堆文本来说是相当大的…),我经常遇到读取超时异常

我相信这不是一个网络问题,因为我尝试过使用curl发出相同的请求,但响应很快就到达了,大约两秒钟

当我查看网络中发生的事情(使用wireshark捕获数据包)时,我注意到我的计算机中的TCP接收窗口在某个时刻变得满了。TCP协议栈有时会在这种情况下幸存下来;我可以看到服务器发送TCP keep alive以保持连接,但最终TCP连接中断


可能是代码的读取部分(一个字符接一个字符地追加接收到的响应)使我的代码变慢了吗?有没有更有效的方法读取HTTP响应

是的,一个字符一个字符地读是相当慢的。尝试一次将块读入缓冲区:

char[] buf = new char[2048];
int charsRead;
while((charsRead = rd.read(buf, 0, 2048)) > 0) {
    response.append(buf, 0, charsRead);
}

正如Phil已经说过的,逐字节读取流有点慢。我更喜欢使用BufferedReader的readLine()方法:

StringBuilder response = new StringBuilder();
String line = "";
while((line = rd.readLine()) != null) {
    response.append(line + System.getProperty("line.separator");
}
如果可能的话,我会考虑使用Apache HTTP客户端库。它易于使用,并且在处理HTTP内容时非常强大。

您还应该记住设置套接字和连接超时。通过这种方式,您可以控制连接保持打开的时间(至少在连接的您一侧)

最后但并非最不重要的一点是,在收到响应后,始终在finally块中关闭HTTP连接,否则可能会遇到打开文件过多的问题


希望这是heps;)

那很有效,非常感谢!现在我意识到这真的是一个愚蠢的问题:)