Вопрос проверяет умение эффективно читать конец больших файлов, что важно для анализа логов или данных, не загружая весь файл в память.
Чтение последних строк файла — частая задача при анализе логов, мониторинге или обработке данных, где важен только свежий контент. Загружать весь файл в память неэффективно, особенно для файлов размером в гигабайты. Вместо этого используются методы, которые читают файл с конца.
Основная идея — открыть файл, переместиться (seek) ближе к концу и читать блоки данных в обратном порядке, пока не будет найдено нужное количество строк. Это можно сделать:
tail -n 10 file.log в Linux.Вот функция, которая читает последние N строк файла, эффективно используя seek:
def tail_file(filename, n=10):
with open(filename, 'rb') as f:
# Перемещаемся в конец файла
f.seek(0, 2)
file_size = f.tell()
block_size = 1024
data = []
lines_found = 0
# Читаем блоки с конца
while file_size > 0 and lines_found < n:
read_size = min(block_size, file_size)
f.seek(file_size - read_size)
block = f.read(read_size).decode('utf-8', errors='ignore')
file_size -= read_size
# Считаем строки в блоке
lines = block.split('\n')
# Первая часть блока может быть обрезанной строкой
if len(data) > 0:
data[-1] = lines[-1] + data[-1]
lines = lines[:-1]
data = lines + data
lines_found = len(data)
return data[-n:]
# Использование
last_lines = tail_file('app.log', 5)
for line in last_lines:
print(line)В Node.js можно использовать модуль fs для похожего подхода:
const fs = require('fs');
const readLastLines = (filePath, maxLines) => {
const stats = fs.statSync(filePath);
const bufferSize = 1024;
let lines = [];
let lineCount = 0;
let position = stats.size;
while (position > 0 && lineCount < maxLines) {
const length = Math.min(bufferSize, position);
const buffer = Buffer.alloc(length);
const fd = fs.openSync(filePath, 'r');
fs.readSync(fd, buffer, 0, length, position - length);
fs.closeSync(fd);
const chunk = buffer.toString('utf-8');
const chunkLines = chunk.split('\n');
if (lines.length > 0) {
lines[0] = chunkLines.pop() + lines[0];
}
lines = chunkLines.concat(lines);
lineCount = lines.length;
position -= length;
}
return lines.slice(-maxLines);
};
// Использование
const lines = readLastLines('server.log', 5);
console.log(lines);Вывод: Используйте чтение с конца файла, когда нужно быстро получить последние записи из больших логов или данных, не тратя ресурсы на полную загрузку файла. Это особенно полезно в DevOps, мониторинге и приложениях реального времени.
Уровень
Рейтинг:
3
Сложность:
4
Навыки
Python
Linux
Ключевые слова
Подпишись на Python Developer в телеграм