Сокеты: блоки bufferedreader readLine()


Я использую метод BufferedReader.readLine() для чтения ответа с удаленного сервера (который написан на C и у меня нет доступа к исходному коду).

BufferedReader br = new BufferedReader(new InputStreamReader(in));
String line;
while((line = br.readLine())!=null){
    [...]
}
Но он всегда блокируется в последней строке, пока не истечет время ожидания. Поэтому я использовал следующий код:
int b;
while(true){
   b = in.read;
   [...]
}

И я обнаружил, что последний прочитанный байт имеет целое значение 13, которое я думаю, что это возврат каретки, верно?

Так почему же блокируется метод readLine? Как сервер обычно сигнализирует о достижении конца потока? Спасибо.

4 12

4 ответа:

В случае сетевого соединения поток завершается, когда сокет закрыт.

Поэтому совершенно нормально, что readLine() блокирует, пока не получит "конец линии" или вы не закроете вручную соединение. Когда ваш readLine() получает последний символ со значением '13', строка считывается и цикл начинается снова, ожидая следующей строки.

Нет никакой разницы между" последней строкой " и другими строками.

Чтобы остановить цикл, необходимо вручную закройте соединение где-нибудь или дождитесь тайм-аута. Но без дополнительной информации о вашем протоколе связи, невозможно быть более точным об этом.

Это зависит от протокола. Если сервер не закроет поток, readLine будет блокироваться до тех пор, пока не будет получен правильный конец строки. Поэтому, если сервер никогда не отправляет правильный конец строки, вы блокируетесь. Возможно, вам следует использовать более низкоуровневые методы и попытаться получить документацию по протоколу или провести ее реинжиниринг.

Убедитесь, что код сервера вышел.println() вместо out.print ()

Вы можете продлить условие while, если не используете пустые строки:

while((line = br.readLine())!=null && line.length() > 0) {
   // ...
}