2014-03-12 72 views
0

删除从列表中的项目,我有以下方法:通过比较日期

public List<List<String>> compareDate(List<List<String>> lists,String from, String to) { 

    String dateFromLog; 
    Date fromDate = null; 
    Date toDate = null; 

    SimpleDateFormat sdfToDateTime = new SimpleDateFormat(
      "yyyyMMdd HH:mm:ss"); 
    SimpleDateFormat sdfToDate = new SimpleDateFormat("yyyyMMdd"); 

    try { 
     fromDate = sdfToDate.parse(from); 
     toDate = sdfToDate.parse(to); 
    } catch (ParseException e) { 
     e.printStackTrace(); 
    } 

    for (int i = 0; i < lists.size(); i++) { 
     dateFromLog = lists.get(i).get(0); 
     try { 
      Date logDate = sdfToDateTime.parse(dateFromLog); 

      if (fromDate.before(logDate)) { 
       lists.remove(i); 
      } else if (toDate.after(logDate)) { 
       lists.remove(i); 
      } 

     } catch (ParseException ex2) { 
      ex2.printStackTrace(); 
     } 
    } 
    return lists; 
} 

我有一些麻烦与如果在try catch块。我想删除此列表中的每个条目,其中logDate位于fromDate之前和toDate之后。不幸的是,它删除了一些列表,但不是全部。

我在做什么错在这里?

非常感谢提前!

+0

使用iterator类中删除元素 – Kick

回答

3

您不应该使用索引来转发遍历列表并删除该循环中的元素,因为可以跳过这些元素。

问题如下:

假设索引2,3和4处的元素匹配。现在您处于i = 2并删除元素2. 所有后续元素都将移动,因此元素3现在位于索引2,元素4位于索引3处。在下一次迭代中,i将增加为3,因此您将检查元素4,有效地跳过元素3.

解决方法是向后迭代或使用迭代器。

使用迭代器的首选方式:

for (Iteratory<List<String> itr = lists.iteator(); itr.hasNext();) { 
    List<String> elementList = itr.next(); 
    ... 

    if(...) { 
    itr.remove(); 
    } 
} 

相反的方式(不推荐):

for (int i = lists.size() - 1; i >= 0 ; i--) { 
    ... 
} 
+0

大,为快速的答案,好非常感谢说明。我会记住它的:-) – user3410442

3

在迭代Collection时,应通过Iterator.remove完成元件去除。否则,未定义的行为可能会发生。

for (Iterator<List<String>> it = lists.iterator(); it.hasNext();) { 
    List<String> aList = it.next(); 
    if (mustRemove(aList)) { 
     it.remove(); 
    } 
} 

The Collection Interface在Java教程:

注意Iterator.remove是在迭代修改集合的唯一安全的方法;如果在迭代过程中以任何其他方式修改了基础集合,则行为是未指定的。

此外,如果您在使用第三方库的位置的时候,你可以用一个Predicate,将删除从List不需要的元素一起使用Apache下议院选集CollectionUtils.filter()