Подтвердить что ты не робот

Java BufferedReader вернется к началу текстового файла?

В настоящее время у меня есть 2 BufferedReader, инициализированный в том же текстовом файле. Когда я закончил читать текстовый файл с первым BufferedReader, я использую второй, чтобы сделать другой проход через файл сверху. Необходимы несколько проходов по одному и тому же файлу.

Я знаю о reset(), но ему должно предшествовать вызов mark(), а mark() должен знать размер файла, что-то, о чем я не думаю, что мне нужно будет беспокоиться.

Идеи? Пакеты? Libs? Код?

Спасибо TJ

4b9b3361

Ответ 1

В чем недостаток простого создания нового BufferedReader для чтения сверху? Я бы ожидал, что операционная система будет кэшировать файл, если он достаточно мал.

Если вы беспокоитесь о производительности, доказали ли вы, что это узкое место? Я просто делал бы самую простую вещь и не беспокоился об этом, пока у тебя не возникнет какая-то конкретная причина. Я имею в виду, вы могли бы просто прочитать все это в памяти, а затем сделать два прохода на результат, но опять же это будет сложнее, чем просто читать с самого начала с новым читателем.

Ответ 2

Буферизованные считыватели предназначены для последовательного чтения файла. Что вы ищете, это java.io.RandomAccessFile, а затем вы можете использовать seek(), чтобы доставить вас туда, где вы хотите в файле.

Считыватель произвольного доступа реализуется так:

try{
     String fileName = "c:/myraffile.txt";
     File file = new File(fileName);
     RandomAccessFile raf = new RandomAccessFile(file, "rw");
     raf.readChar();
     raf.seek(0);
} catch (FileNotFoundException e) {
     // TODO Auto-generated catch block
     e.printStackTrace();
} catch (IOException e) {
     // TODO Auto-generated catch block
     e.printStackTrace();
}

"rw" - это символ режима, который подробно описан здесь.

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

Ответ 3

Лучший способ продолжить - это изменить алгоритм таким образом, чтобы вам не понадобился второй проход. Я использовал этот подход пару раз, когда мне приходилось иметь дело с огромными (но не ужасными, то есть несколькими ГБ) файлами, которые не соответствовали доступной памяти.

Это может быть сложно, но прирост производительности обычно стоит усилий

Ответ 4

О знаке / reset:

Метод меток в BufferedReader принимает параметр readAheadLimit, который ограничивает, насколько далеко вы можете прочитать после отметки до reset становится невозможным. Сброс фактически не означает поиск файловой системы (0), он просто ищет внутри буфера. Процитировать Javadoc:

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

Ответ 5

"Весь бизнес о методах() и reset() в BufferedReader имеет плохой дизайн.

почему вы не расширяете этот класс и не делаете его в конструкторе(), а затем выполняете поиск (0) в методе topOfFile().

BR,
~ А