2016-12-13 5 views
2

Я использую компаратор для сортировки файлов по дате изменения. Эти файлы должны обрабатываться для содержащихся данных и удаляться после. Я должен убедиться, что файлы находятся в последовательном порядке перед их обработкой. Ниже я до сих пор.Каков правильный способ обработки IOException в компараторе?

public class FileComparator implements Comparator<Path> { 
    @Override 
    public int compare(Path o1, Path o2) { 
     try { 
      return Files.getLastModifiedTime(o1).compareTo(Files.getLastModifiedTime(o2)); 
     } catch (IOException exception) { 
      //write to error log 
      //*** 
     } 
    } 
} 

*** Здесь я застрял. Мне нужно вернуть int, потому что для этого требуется сравнение, но я не хочу возвращать нуль и иметь ложную эквивалентность, когда он терпит неудачу.

Я пробовал реструктурировать код, но если getLastModifiedTime() не работает, o1Modified и o2Modified будут иметь значение null.

public class FileComparator implements Comparator<Path> { 
    @Override 
    public int compare(Path o1, Path o2) { 
     FileTime o1Modified = null; 
     FileTime o2Modified = null;   
     try { 
      o1Modified = Files.getLastModifiedTime(o1); 
      o2Modified = Files.getLastModifiedTime(o2); 
     } catch (IOException exception) { 
      //write to error log 

     } 

     return o1Modified.compareTo(o2Modified); 

    } 
} 

Есть ли стандартный способ справиться с такими ситуациями?

+2

Если вы получили «IOException», подразумевается, что с вашим путем (-ами) что-то не так. Если один (или оба) ваших путей указывают на файл, который не существует, не имеет смысла говорить, что они неравны? Вы можете сортировать это, как хотите (путем возврата либо -1, либо 1, в зависимости от конкретного случая). Другой способ сказать, что все недопустимые пути одинаково недействительны. – Hypino

ответ

4

Я думаю, что способ решить эту конкретную ситуацию - вызывать Files.getLastModifiedTime() на каждом пути ровно один раз, сохраняя результаты, а затем используя сохраненные результаты во время сортировки.

Это имеет ряд преимуществ:

  1. Это чисто решает IOException проблему.

  2. Он не многократно и неоправданно выполняет одни и те же дорогостоящие операции ввода-вывода в тех же файлах.

  3. Он обеспечивает согласованное упорядочение, даже если последнее время изменения файла изменяется на полпути через сортировку (см., Например, "Comparison method violates its general contract!", как это могло бы тонко разбить ваш код).

+1

Хороший ответ, который решает проблему по первопричине, а не по полосе. – HNA

2

Бросить исключение во время выполнения оборачивания IOException:

try { 
     return Files.getLastModifiedTime(o1).compareTo(Files.getLastModifiedTime(o2)); 
    } catch (IOException e) { 
     throw new UncheckedIOException("impossible to get last modified dates, so can't compare", e) 
    } 

Заметим, однако, что измененное время может измениться в течение рода, что сделало бы ваш компаратор неправильно: он не будет больше уважать свой контракт. Таким образом, лучший подход состоял бы в том, чтобы сначала выполнить итерацию по вашим путям и обернуть их в некоторый объект TimedPath, который сохранит последнее время модификации, а затем отсортирует те объекты TimedPath.

+0

Благодарим вас за предложение объекта TimedPath. Ответ NPE решает мою проблему, и ваше предложение о создании объекта, ориентированного на время, улучшает решение. – HNA

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