Лучший способ прочитать огромный файл (например, очень большой текстовый документ)
Я новичок в Java ... в моем текущем проекте мне нужно прочитать и написать очень большой текстовый файл (1 ГБ - 5 ГБ)... сначала я использовал следующие классы: BufferedReader и BufferedWriter
public static String read(String dir) {
BufferedReader br;
String result = "", line;
try {
br = new BufferedReader(new InputStreamReader(new FileInputStream(dir), "UTF-8"));
while ((line = br.readLine()) != null) {
result += line + "\n";
}
} catch (IOException ex) {
//do something
}
return result;
}
public static void write(String dir, String text) {
BufferedWriter bw;
try {
bw = new BufferedWriter(new OutputStreamWriter(new FileOutputStream(dir), "UTF-8"));
bw.write("");
for (int i = 0; i < text.length(); i++) {
if (text.charAt(i) != '\n') {
bw.append(text.charAt(i));
} else {
bw.newLine();
}
}
bw.flush();
} catch (IOException ex) {
//do something
}
}
этот класс работает очень хорошо, но не для огромных файлов...
Затем я использовал MappedByteBuffer для read()
метод (я не знаю, как написать файл, используя этот класс):
public static String read(String dir) {
FileChannel fc;
String s = "";
try {
fc = new RandomAccessFile(dir, "r").getChannel();
MappedByteBuffer buffer = fc.map(FileChannel.MapMode.READ_ONLY, 0, fc.size());
buffer.load();
buffer.force();
for (int i = 0; i < buffer.limit(); i++) {
s += (char) buffer.get();
} //I know the problem is here
buffer.clear();
inChannel.close();
} catch (IOException e) {
//do something
}
return s;
}
Но по-прежнему не может читать большие файлы (более 30-40 МБ), даже Блокнот работает быстрее, чем мое приложение:))
а также еще одна проблема, я не знаю, как изменить кодировку вторым способом (например, "UTF-8", "ANSI",...)
ребята, скажите, пожалуйста, как лучше всего читать и записывать файлы laaaarge? любая идея?
5 ответов
По крайней мере, я бы рекомендовал изменить
result += line + "\n";
к StringBuilder.
resultBldr.append(line).append("\n");
Это позволяет избежать создания нового строкового объекта - большего и большего, большего и большего строкового объекта!- в каждой строке.
Кроме того, вы должны обязательно записать свой вывод в файл построчно. Не накапливайте весь этот текст, а затем выводите его.
Другими словами, в этой ситуации полное разделение между вашими read
а также write
функции не рекомендуется.
result += line + "\n";
эта строка пытается сохранить все содержимое файла в памяти. Попробуйте обработать каждую строку, как вы читаете это так
while ((line = br.readLine()) != null) {
processLine( line ); // this may write it to another file.
}
Всегда плохо читать файлы большого размера в диапазоне от 1 ГБ до 5 ГБ за один раз. Будет огромная производительность, и ваше приложение будет замедляться.
Лучше разбить этот огромный файл на более мелкие куски и прочитать его по частям. Я думаю, что если вы начнете читать файлы небольшими порциями, код, который вы написали, будет работать отлично.
Вы слышали о системе HDFS, индексации Solr, платформах Apache Hadoop, которые специально предназначены для работы с большими данными. Возможно, вы захотите взглянуть на это.
Подумайте, что каждое связывание строк создает новую строку, поэтому, если вы читаете каждый символ большого файла размером 40 МБ и объединяете, вы создаете в общей сложности 40 000 000 строк в read()
,
Попробуй использовать StringBuffer
вместо String
Рекомендую для этой ситуации.
Лучше использовать класс Scanner, поскольку он использует поток, и попытаться отправить содержимое в БД, поскольку БД может хранить больше данных, чтобы вы могли выполнять с данными что угодно. для чтения данных используйте запрос с ограничением FETCH. Я использовал это для файла размером 3 ГБ, и он работает без каких-либо проблем.