Кажется, что все здесь думают, что реализация Runnable - это путь, и я на самом деле не согласен с ними, но, на мой взгляд, есть также причина для расширения Thread, фактически вы как бы продемонстрировали это в своем коде.
Если вы реализуете Runnable, то класс, реализующий Runnable, не будет контролировать имя потока, это вызывающий код, который может установить имя потока, например:
new Thread(myRunnable,"WhateverNameiFeelLike");
, но если вы расширяете Thread затем вы можете управлять этим внутри самого класса (как в вашем примере вы называете поток «ThreadB»). В этом случае вы:
A) могли бы дать ему более полезное имя для целей отладки
B) принудительно использовать это имя для всех экземпляров этого класса (если вы не игнорируете факт что это поток, и делайте вышеизложенное с ним, как будто это Runnable, но мы в любом случае говорим здесь о соглашении, поэтому я могу игнорировать эту возможность, которую я чувствую).
Вы можете даже, например, взять трассировку стека его создания и использовать его в качестве имени потока. Это может показаться странным, но в зависимости от структуры вашего кода это может быть очень полезно для целей отладки.
Это может показаться незначительным, но когда у вас очень сложное приложение с большим количеством потоков и все вдруг «остановилось» (либо по причине тупиковой ситуации, либо, возможно, из-за недостатка сетевого протокола, который было бы менее очевидно - или по другим бесконечным причинам), тогда получение дампа стека из Java, где все потоки называются «Thread-1», «Thread-2», «Thread-3», не всегда очень полезно (это зависит от того, как ваши потоки структурированы и можете ли вы с пользой определить, что есть что, просто по их трассировке стека - это не всегда возможно, если вы используете группы из нескольких потоков, выполняющих один и тот же код).
Сказав, что вы, конечно, также можете сделать вышеупомянутое универсальным способом, создав расширение класса потока, которое устанавливает его имя в виде трассировки стека его вызова создания, а затем использует это с вашими реализациями Runnable вместо стандартного Класс потока Java (см. ниже), но в дополнение к трассировке стека может быть более специфичная для контекста информация, которая будет полезна в имени потока для отладки (ссылка на одну из множества очередей или сокетов, которые он может обработать, например, в этом случае вы может предпочесть расширить Thread специально для этого случая, чтобы вы могли заставить компилятор заставить вас (или других пользователей, использующих ваши библиотеки) передавать определенную информацию (например, соответствующую очередь / сокет) для использования в имени).
Вот пример общего потока с трассировкой вызывающего стека в качестве имени:
public class DebuggableThread extends Thread {
private static String getStackTrace(String name) {
Throwable t= new Throwable("DebuggableThread-"+name);
ByteArrayOutputStream os = new ByteArrayOutputStream();
PrintStream ps = new PrintStream(os);
t.printStackTrace(ps);
return os.toString();
}
public DebuggableThread(String name) {
super(getStackTrace(name));
}
public static void main(String[] args) throws Exception {
System.out.println(new Thread());
System.out.println(new DebuggableThread("MainTest"));
}
}
и вот пример выходных данных, сравнивающих два имени:
Thread[Thread-1,5,main]
Thread[java.lang.Throwable: DebuggableThread-MainTest
at DebuggableThread.getStackTrace(DebuggableThread.java:6)
at DebuggableThread.<init>(DebuggableThread.java:14)
at DebuggableThread.main(DebuggableThread.java:19)
,5,main]
Думаю, вам нужно будет проверить время модификации каталога и подкаталога (для добавляемых / удаляемых файлов) и время модификации файла (для изменений в каждом файле).
Напишите рекурсивную процедуру, которая проверяет каталог на предмет наличия это время модификации и, если оно изменено, плюс каждый файл. Затем проверяет содержимое каталога и рекурсивно вызывает любые подкаталоги. Вы должны просто иметь возможность проверить любое время модификации, превышающее время последней проверки.
РЕДАКТИРОВАТЬ: Поскольку я написал выше, Java 7 вышла со своим возможность просмотра каталогов .
Здесь список возможных решений и пример простого Наблюдателя за файлами / папками .
Если вы можете использовать Java 7, он поддерживает независимые от платформы уведомления об изменении каталога / файла.
JNA имеет образец для уведомления об изменении кросс-платформы здесь . Не уверен, насколько легко вам это может показаться.
] Не знаю, хорошо ли это, но вот взгляд одного человека на проблему.
Похоже, в .NET есть что-то встроенное: FileSystemWatcher
ОБНОВЛЕНИЕ: Благодаря kd304 я только что узнал, что в Java 7 будет такая же функция . Сегодня ничего хорошего вам не принесет, если вы не воспользуетесь предварительным выпуском .
Вам необходимо просматривать каждый файл, отслеживать атрибут File.lastModified
и проверять флаг File.exists
вместе с небольшой простой рекурсией для обхода структуры каталогов.
с NIO2 (Java7) это будет очень просто. С помощью Java6 вы можете вызывать list () и сравнивать с предыдущим списком раз в секунду? (Служба наблюдения за бедным человеком)