bufferedreader — читать в stringbuffer, а не в строку

У меня есть следующий код. Что я хотел бы сделать, так это прочитать каждую строку из BufferedReader непосредственно в StringBuffer, чтобы уменьшить накладные расходы памяти. Как только он дойдет до конца потока данных, я бы хотел, чтобы он вышел из цикла while.

StringBuffer line = new StringBuffer();
        URL url = new URL("a url");
        BufferedReader reader = new BufferedReader(new InputStreamReader(url.openStream()));
                int count = 0;
                while(line.append(reader.readLine()) != null){
                    System.out.println(line.toString());
                    line.delete(0,line.length());
                }

Он отлично читает поток, но когда я дохожу до конца потока, он возвращает ноль и продолжает печатать ноль, не выходя из цикла. Любой


person user1958884    schedule 01.02.2013    source источник
comment
Я думаю, что используйте for(String line; (line = reader.readLine()) != null;) { ... } только для создания ссылок.   -  person Paul Vargas    schedule 01.02.2013
comment
Почему вы читаете StringBuffer только для того, чтобы удалить его после распечатки строки. Почему бы просто не распечатать строку напрямую?   -  person Marc Baumbach    schedule 01.02.2013
comment
В. Как результат append() может быть нулевым? А. Не может.   -  person user207421    schedule 01.02.2013


Ответы (3)


Это while(line.append(reader.readLine()) != null) в основном то же самое, что сказать while(line.append(reader.readLine()).toString() != null), что вряд ли произойдет.

Другая проблема, которая у вас может возникнуть, заключается в том, что null на самом деле переводится в буквальное String из "null". Вот почему он печатает «null», значение на самом деле не null - еще не запутался...

Вместо этого попробуйте что-то вроде...

String text = null;
while((text = reader.readLine()) != null){
    line.append(text)
    System.out.println(line.toString());
    line.delete(0,line.length());
}

Обновлено

Пока я здесь, могу предположить, что вы на самом деле ничего не спасаете для себя.

readLine создаст объект String, который вы помещаете в файл StringBuffer. На самом деле вы не экономите память, а скорее усложняете процесс.

Если вы действительно беспокоитесь о создании большого количества объектов String в памяти, используйте вместо этого BufferedReader#read(char[]). Добавьте полученный массив символов к StringBuffer.

Кроме того, если вам не нужен синхронизированный доступ к StringBuffer, используйте вместо этого StringBuilder, это быстрее.

person MadProgrammer    schedule 01.02.2013
comment
Я читаю в строковый буфер и использую split (,), который входит в массив. Я мог бы читать до и более 1000 строк, поэтому я хотел бы снизить использование памяти. Но я попробую предложение char. - person user1958884; 01.02.2013
comment
Вы должны понимать, что reader.readLine() уже создал объект String, поэтому любые выгоды, которые, по вашему мнению, вы получаете от использования StringBuffer, подлежат обсуждению. Сказав, что String = String + String в конечном итоге создает один дополнительный объект String для каждой конкатенации (я думаю, 3 в этом примере), так что вы немного экономите себя - person MadProgrammer; 01.02.2013

Это работает отлично. Вам просто нужно поймать NUllPointerException

while(line.append(reader.readLine().toString()) != null){ 
person user1958884    schedule 01.02.2013
comment
Насколько мне известно, StringBuffer преобразует значение null в String литерал null - person MadProgrammer; 01.02.2013
comment
Это странно, потому что System.out.println(new StringBuffer().append((String)null).toString() == null) возвращает false для меня. - person MadProgrammer; 01.02.2013
comment
На самом деле, теперь я прочитал это: P, reader.readLine().toString() вызовет NullPointerException - person MadProgrammer; 01.02.2013

Вы можете попробовать то же самое с этим циклом for:

for (String line; (line = reader.readLine()) != null;) {
    System.out.println(line); // Or whatever
}
person mfaerevaag    schedule 01.02.2013