Sì, ci sono numerosi listener disponibili per le directory, ma sono tutti relativamente complicati e la maggior parte coinvolge i thread.
Pochi giorni fa sono finito in una discussione quasi riscaldata con uno dei nostri tecnici sul fatto che fosse un ammissibile la creazione di un nuovo thread (in un'applicazione web) semplicemente per monitorare un albero di directory. Alla fine sono d'accordo con lui, ma in virtù del fatto di inventare qualcosa di così veloce che non è necessario avere un ascoltatore. Nota: la soluzione descritta di seguito funziona solo se non è necessario conoscere quale file è stato modificato, solo che il file a è stato modificato.
Fornisci il seguente metodo con una raccolta di file (ad es., ottenuto tramite il metodo FileUtils.listFiles() di Apache IO e restituisce un hash per la raccolta. Se un file viene aggiunto, cancellato o modificato la sua data di modifica, l'hash cambierà.
Nei miei test, i file 50K richiedono circa 750ms su una scatola Linux 3Ghz. Toccando uno qualsiasi dei file si modifica l'hash. Nella mia implementazione sto usando un algoritmo di hash diverso (DJB) che è un po 'più veloce, ma questo è il senso. Ora archiviamo l'hash e controlliamo ogni volta perché è piuttosto semplice, soprattutto per le raccolte di file più piccole. Se qualcosa cambia, reindicizziamo la directory. La complessità di un osservatore non valeva la pena nella nostra applicazione.
/**
* Provided a directory and a file extension, returns
* a hash using the Adler hash algorithm.
*
* @param files the Collection of Files to hash.
* @return a hash of the Collection.
*/
public static long getHash(Collection<File> files)
{
Adler32 adler = new Adler32();
StringBuilder sb = new StringBuilder();
for (File f : files) {
String s = f.getParent()+'/'+f.getName()+':'+String.valueOf(f.lastModified());
adler.reset();
adler.update(s.getBytes());
sb.append(adler.getValue()+' ');
}
adler.reset();
adler.update(sb.toString().getBytes());
return adler.getValue();
}
E sì, c'è spazio per migliorare (per esempio, usiamo un metodo di hash piuttosto che inlining esso). Quanto sopra è ridotto dal nostro codice attuale, ma dovrebbe darvi una buona idea di ciò che abbiamo fatto.
fonte
2012-06-27 11:56:09