2010-10-27 2 views
0

Java IO implementation of unix/linux "tail -f" имеет аналогичную проблему; но решение не является жизнеспособным для файлов журналов, которые генерируют около 50-100 строк в секунду.Java - RandomAccessFile (эмуляция функции хвоста Linux)

У меня есть алгоритм, который эмулирует функциональность хвоста в Linux. Например,

File _logFile = new File("/tmp/myFile.txt"); 
long _filePtr = _logFile.length(); 

while (true) 
{ 
    long length = _logFile.length(); 
    if (length < _filePtr) 
    { 
      // means file was truncated 
    } 
    else if (length > _filePtr) 
    { 
      // means something was added to the file 
    } 
// we ignore len = _filePtr ... nothing was written to file 
} 

Моя проблема в том, когда: «что-то добавить в файл» (со ссылкой на заявление еще если()).

else if (length > _filePtr) 
{ 
    RandomAccessFile _raf = new RandomAccessFile(_logFile, "r"); 
    raf.seek(_filePtr); 

    while ((curLine = raf.readLine()) != null) 
      myTextPane.append(curLine); 

     _filePtr = raf.getFilePointer(); 
     raf.close(); 
} 

программные блоки в то время как ((CurLine = raf.readLine()) .... через 15 секунд во время выполнения (Примечание:. Что программа работает прямо в течение первых 15 секунд)

оказывается, что raf.readLine() никогда не бил NULL, потому что я считаю этот файл журнала записывается так быстро, что мы идем в «бесконечный кошки и мыши» петли.

что это лучший способ для подражания Linux хвост?

ответ

2

Я бы подумал, что вам лучше всего будет хватать блок b ytes на основе длины файла, затем отпустите файл и проанализируйте ByteArrayInputStream (вместо того, чтобы пытаться читать непосредственно из файла).

Так что используйте RandomAccessFile # read (byte []) и размер буфера, используя длину возвращаемого файла. Вы не всегда будете показывать точный конец файла, но этого следует ожидать с помощью такого алгоритма опроса.

Как в стороне, этот алгоритм ужасен - вы выполняете операции ввода-вывода в сумасшедшем жестком цикле - вызовы в File # length() будут блокироваться, но не очень. Ожидайте, что эта процедура займет ваше приложение на коленях с процессором. У меня не обязательно есть лучшее решение для вас (ну, на самом деле, я знаю, что исходное приложение записывает в поток вместо файла, но я признаю, что это не всегда возможно).

В дополнение к вышесказанному вы можете ввести задержку опроса (спящий поток на 100 мс каждый цикл) - он выглядит так, как будто вы показываете графический интерфейс - задержка в 100 мс никому не повредит, и значительно улучшают производительность операций качания).

ok - финальная говядина: вы настраиваете компонент Swing из того, что (я надеюсь) код не работает на EDT. Используйте SwingWorker # invokeLater() для обновления вашей текстовой панели.

+0

Благодаря Кевин! Можете ли вы уточнить, что означает «EDT» в вашем последнем абзаце? –

+2

Event Dispatch Thread - быстрый ответ на эту фразу даст вам то, что вам нужно знать. Длинные и короткие: недопустимо вносить изменения состояния в компоненты Swing, если вы не делаете это из EDT. –

0

Похоже, что я нашел проблему и создал решение.

Под еще, если заявление:

while ((curLine = raf.readLine()) != null) 
    myTextPane.append(curLine); 

Это была проблема. метод append (String) myTextPane (который является производным классом JTextPane) вызвал «setCaretPosition()» на каждой строке append, которая НЕОБХОДИМА!

Это означает, что setCaretPosition() был вызван 50-100 Гц, пытаясь «прокрутить вниз». Это вызвало блокировку служебных данных интерфейса.

Простым решением было создание класса StringBuffer и добавление «curLine» до тех пор, пока raf.readLine() не будет прочитан.

Затем добавьте StringBuffer и voila ... больше не блокируйте setCaretPosition()!

Благодаря Кевину за то, что он привел меня в правильном направлении.

0

Вы всегда могли EXEC программу хвост:

BufferedReader in = new BufferedReader(new InputStreamReader(
      Runtime.getRuntime().exec("tail -F /tmp/myFile.txt").getInputStream())); 
    String line; 
    while ((line = in.readLine()) != null) { 
     // process line 
    } 
+0

К сожалению, этот подход редко работает. – chrisapotek

 Смежные вопросы

  • Нет связанных вопросов^_^