使用List中的remove方法遇到的坑


場景...

remove方法

list中根據判斷條件符合的就remove掉一個數據

 public static void main(String[] args) {
        List<CaseHead> list=new ArrayList<CaseHead>();
        CaseHead caseHead1=new CaseHead();
        caseHead1.setCaseid("a");
        CaseHead caseHead2=new CaseHead();
        caseHead2.setCaseid("b");
        CaseHead caseHead3=new CaseHead();
        caseHead3.setCaseid("c");
        CaseHead caseHead4=new CaseHead();
        caseHead4.setCaseid("d");
        CaseHead caseHead5=new CaseHead();
        caseHead5.setCaseid("e");
        list.add(caseHead1);
        list.add(caseHead2);
        list.add(caseHead3);
        list.add(caseHead4);
        list.add(caseHead5);


        List<String> list2=new ArrayList<String>();
        list2.add("a");
        list2.add("b");

        for (int i = 0; i < list.size(); i++) {
            String caseid=list.get(i).getCaseid();
            for (int j = 0; j <list2.size() ; j++) {
                String l=list2.get(j);
                if (caseid.equals(l)){
                    list.remove(i);
                }
            }


        }

        for (int a = 0; a < list.size(); a++) {
            System.out.println(list.get(a).getCaseid());
        }}

結果是什么?

根據以上代碼,希望得到的結果是 cde 但是運行結果是bcde那么問題來了為什么會得到一下結果呢?

 

 

 先看一下list remove的源碼

// 刪除ArrayList指定位置的元素
    public E remove(int index) {
        RangeCheck(index);//檢查index是否超出list大小范圍,否則拋出異常
        modCount++;
        E oldValue = (E) elementData[index];//elementData是實現list的數組
        int numMoved = size - index - 1;//當執行刪除操作是后面的元素全部向前面移動一位
        if (numMoved > 0)
            System.arraycopy(elementData, index+1, elementData, index,
                 numMoved);
        elementData[--size] = null;
        return oldValue;
    }
    // 刪除ArrayList的指定元素
    public boolean remove(Object o) {
        if (o == null) {
          for (int index = 0; index < size; index++)
             if (elementData[index] == null) {
                 fastRemove(index);
                return true;
            }
        } else {
            for (int index = 0; index < size; index++)
              if (o.equals(elementData[index])) {
                  fastRemove(index);
                  return true;
              }
        }
        return false;
   }
  //快速刪除第index個元素
  private void fastRemove(int index) {
        modCount++;  
        int numMoved = size - index - 1;  
        if (numMoved > 0)  
            System.arraycopy(elementData, index+1, elementData, index,  
                             numMoved);  
        elementData[--size] = null; 
   } 

源碼可知,List在刪除指定位置的對象時,執行刪除操作是后面的元素全部向前面移動一位

因為,當你remove掉一個對象時,list的就少了一個 index 0的被remove了,之前index 1的數據就自動變為index 0了arrayList是有順序數組,從0開始。如果從前開始刪除實際上就相當於跳着刪除了。

解決辦法1:

每次刪除之后i--自動返回到上一個index開始

public static void main(String[] args) {
        List<CaseHead> list=new ArrayList<CaseHead>();
        CaseHead caseHead1=new CaseHead();
        caseHead1.setCaseid("a");
        CaseHead caseHead2=new CaseHead();
        caseHead2.setCaseid("b");
        CaseHead caseHead3=new CaseHead();
        caseHead3.setCaseid("c");
        CaseHead caseHead4=new CaseHead();
        caseHead4.setCaseid("d");
        CaseHead caseHead5=new CaseHead();
        caseHead5.setCaseid("e");
        list.add(caseHead1);
        list.add(caseHead2);
        list.add(caseHead3);
        list.add(caseHead4);
        list.add(caseHead5);


        List<String> list2=new ArrayList<String>();
        list2.add("a");
        list2.add("b");

        for (int i = 0; i < list.size(); i++) {
            String caseid=list.get(i).getCaseid();
            for (int j = 0; j <list2.size() ; j++) {
                String l=list2.get(j);
                if (caseid.equals(l)){
                    list.remove(i);
                    i--;
                }
            }


        }

        for (int a = 0; a < list.size(); a++) {
            System.out.println(list.get(a).getCaseid());
        }
}

 

 

第二種解決方法

倒着刪除從后往前遍歷刪除,從index大的往index小的刪

 public static void main(String[] args) {
        List<CaseHead> list=new ArrayList<CaseHead>();
        CaseHead caseHead1=new CaseHead();
        caseHead1.setCaseid("a");
        CaseHead caseHead2=new CaseHead();
        caseHead2.setCaseid("b");
        CaseHead caseHead3=new CaseHead();
        caseHead3.setCaseid("c");
        CaseHead caseHead4=new CaseHead();
        caseHead4.setCaseid("d");
        CaseHead caseHead5=new CaseHead();
        caseHead5.setCaseid("e");
        list.add(caseHead1);
        list.add(caseHead2);
        list.add(caseHead3);
        list.add(caseHead4);
        list.add(caseHead5);


        List<String> list2=new ArrayList<String>();
        list2.add("a");
        list2.add("b");

        for (int i = list.size()-1; i >= 0; i--) {
            String caseid=list.get(i).getCaseid();
            for (int j = 0; j <list2.size() ; j++) {
                String l=list2.get(j);
                if (caseid.equals(l)){
                    list.remove(i);

                }
            }


        }

        for (int a = 0; a < list.size(); a++) {
            System.out.println(list.get(a).getCaseid());
        }
}

結果如下:

 

 

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM