ArrayList在for循環(huán)中使用remove方法移除元素方法介紹
有時(shí)候我們需要在一個(gè)ArrayList的for循環(huán)中動(dòng)態(tài)刪除元素的需求, 廢話不多說看代碼
List<Integer> list = new ArrayList<Integer>(); list.add(0); list.add(1); list.add(2); list.add(3); list.add(4); list.add(5); list.add(6); list.add(7); //正常循環(huán) for (int i = 0; i < list.size(); i++) { System.out.println("i的值:" + i + " 對應(yīng)的數(shù)字:" + list.get(i)); } System.out.println("沒有remove前l(fā)ist的項(xiàng):"+list.size()); //邊循環(huán)邊刪除 for (int i = 0; i < list.size(); i++) { System.out.println("i的值:" + i + " 對應(yīng)的數(shù)字:" + list.get(i)); if(list.get(i) == 3) list.remove(list.get(i));//刪除list的第四項(xiàng) } System.out.println("remove后list的項(xiàng):"+list.size()); System.out.println("==========remove后的list=========="); for (int i = 0; i < list.size(); i++) { System.out.println("i的值:" + i + " 對應(yīng)的數(shù)字:" + list.get(i)); }
執(zhí)行代碼, 結(jié)果如下:
i的值:0 對應(yīng)的數(shù)字:0 i的值:1 對應(yīng)的數(shù)字:1 i的值:2 對應(yīng)的數(shù)字:2 i的值:3 對應(yīng)的數(shù)字:3 i的值:4 對應(yīng)的數(shù)字:4 i的值:5 對應(yīng)的數(shù)字:5 i的值:6 對應(yīng)的數(shù)字:6 i的值:7 對應(yīng)的數(shù)字:7 沒有remove前l(fā)ist的項(xiàng):8 i的值:0 對應(yīng)的數(shù)字:0 i的值:1 對應(yīng)的數(shù)字:1 i的值:2 對應(yīng)的數(shù)字:2 i的值:3 對應(yīng)的數(shù)字:3 i的值:4 對應(yīng)的數(shù)字:5 i的值:5 對應(yīng)的數(shù)字:6 i的值:6 對應(yīng)的數(shù)字:7 remove后list的項(xiàng):7 ==========remove后的list========== i的值:0 對應(yīng)的數(shù)字:0 i的值:1 對應(yīng)的數(shù)字:1 i的值:2 對應(yīng)的數(shù)字:2 i的值:3 對應(yīng)的數(shù)字:4 i的值:4 對應(yīng)的數(shù)字:5 i的值:5 對應(yīng)的數(shù)字:6 i的值:6 對應(yīng)的數(shù)字:7
可以看到?jīng)]有刪除前, 我們的list的項(xiàng)和循環(huán)對應(yīng)的數(shù)字都是正確的, 但是下面的循環(huán)在刪除第4個(gè)元素后,第4,5,6個(gè)項(xiàng)對應(yīng)的數(shù)字本應(yīng)該是4,5,6, 但是這里卻變成了5,6,7.
原因是,我們刪除第4項(xiàng)后,list的長度就變成7,而且,list會(huì)把第4項(xiàng)后面的值往前移一位, 也就是說,i=3時(shí),list.get(i)=4,i=4時(shí),list.get(i)=5,i=5時(shí),list.get(i)=6,i=6時(shí),list.get(i)=7.. 我們再說的形象一點(diǎn), 就是本來有8層糕點(diǎn),依次是0-7,豎起來,大的在上,小的在下,我們從下往上數(shù),數(shù)到第5個(gè)的時(shí)候,吃掉這一層糕點(diǎn),這時(shí),上面三層分別往下移了一層
所以, 值為4的項(xiàng)我們根本沒有循環(huán)到
那有什么方法可以實(shí)現(xiàn)remove呢, 有個(gè)笨方法,是新建一個(gè)tempList, 把要?jiǎng)h除的項(xiàng)全部add進(jìn)去,最后用list.removeAll(tempList)實(shí)現(xiàn) . 但是這里我們有更好的方法, 就是倒序刪除
還是上面的例子, 我們看代碼:
List<Integer> list = new ArrayList<Integer>(); list.add(0); list.add(1); list.add(2); list.add(3); list.add(4); list.add(5); list.add(6); list.add(7); //正常循環(huán) for (int i = 0; i < list.size(); i++) { System.out.println("i的值:" + i + " 對應(yīng)的數(shù)字:" + list.get(i)); } System.out.println("沒有remove前l(fā)ist的項(xiàng):"+list.size()); //邊循環(huán)邊刪除 for (int i = list.size() -1 ; i >= 0; i--) { System.out.println("i的值 " + i + " 對應(yīng)的數(shù)字 " + list.get(i)); if(list.get(i) == 3) list.remove(list.get(i)); } System.out.println("remove后list的項(xiàng):"+list.size()); System.out.println("==========remove后的list=========="); for (int i = 0; i < list.size(); i++) { System.out.println("i的值 " + i + " 對應(yīng)的數(shù)字 " + list.get(i)); }
執(zhí)行代碼,結(jié)果如下:
i的值:0 對應(yīng)的數(shù)字:0 i的值:1 對應(yīng)的數(shù)字:1 i的值:2 對應(yīng)的數(shù)字:2 i的值:3 對應(yīng)的數(shù)字:3 i的值:4 對應(yīng)的數(shù)字:4 i的值:5 對應(yīng)的數(shù)字:5 i的值:6 對應(yīng)的數(shù)字:6 i的值:7 對應(yīng)的數(shù)字:7 沒有remove前l(fā)ist的項(xiàng):8 i的值 7 對應(yīng)的數(shù)字 7 i的值 6 對應(yīng)的數(shù)字 6 i的值 5 對應(yīng)的數(shù)字 5 i的值 4 對應(yīng)的數(shù)字 4 i的值 3 對應(yīng)的數(shù)字 3 i的值 2 對應(yīng)的數(shù)字 2 i的值 1 對應(yīng)的數(shù)字 1 i的值 0 對應(yīng)的數(shù)字 0 remove后list的項(xiàng):7 ==========remove后的list========== i的值 0 對應(yīng)的數(shù)字 0 i的值 1 對應(yīng)的數(shù)字 1 i的值 2 對應(yīng)的數(shù)字 2 i的值 3 對應(yīng)的數(shù)字 4 i的值 4 對應(yīng)的數(shù)字 5 i的值 5 對應(yīng)的數(shù)字 6 i的值 6 對應(yīng)的數(shù)字 7
我們可以看到變循環(huán)變刪除,并不影響后面的元素, remove后的list也和第一次的結(jié)果是一樣的 . 這是因?yàn)槲覀儎h除list元素,list的長度是會(huì)變小, 但是變化的只是比當(dāng)前被刪除元素的項(xiàng)大的項(xiàng), 而我們這里使用倒序循環(huán), 大的項(xiàng), 我們已經(jīng)執(zhí)行過了, 所以不會(huì)影響.. 再用上面的比喻來說明,這次我們是從上往下數(shù),數(shù)到第4個(gè)的時(shí)候,吃掉這一層糕點(diǎn),這時(shí),上面三層分別往下移了一層 , 但是這不影響我們之前數(shù)過的蛋糕, 而且對下面的蛋糕也不影響, 這就是原理
總結(jié)
以上就是本文關(guān)于ArrayList在for循環(huán)中使用remove方法移除元素方法介紹的全部內(nèi)容,希望對大家有所幫助。感興趣的朋友可以參閱:Java實(shí)現(xiàn)跳躍表(skiplist)的簡單實(shí)例 Java多線程ForkJoinPool實(shí)例詳解 等。感謝朋友們對腳本之家網(wǎng)站的支持。有什么問題或者想要了解的可以隨時(shí)給我們留言,小編會(huì)及時(shí)回復(fù)大家的。
相關(guān)文章
Springboot獲取文件內(nèi)容如何將MultipartFile轉(zhuǎn)File
本文給大家介紹Springboot獲取文件內(nèi)容,將MultipartFile轉(zhuǎn)File方法,本文結(jié)合示例代碼給大家介紹的非常詳細(xì),感興趣的朋友一起看看吧2024-01-01Java中的static和final關(guān)鍵字的使用詳解
這篇文章主要介紹了Java中的static和final關(guān)鍵字的使用詳解, 當(dāng)方法名前有static,即為static方法,可以方便我們無需創(chuàng)建對象也可以調(diào)用此方法,靜態(tài)方法比較拉,只可以訪問 靜態(tài)的 屬性/變量/方法,無法訪問非靜態(tài)的這些屬性/變量/方法,需要的朋友可以參考下2024-01-01springboot項(xiàng)目中出現(xiàn)同名bean異常報(bào)錯(cuò)的解決方法
這篇文章給大家聊聊springboot項(xiàng)目出現(xiàn)同名bean異常報(bào)錯(cuò)如何修復(fù),文中通過代碼示例給大家介紹解決方法非常詳細(xì),對大家的學(xué)習(xí)或工作有一定的幫助,需要的朋友可以參考下2024-01-01windows環(huán)境下java開發(fā)工具maven的安裝教程圖解
Maven是一個(gè)項(xiàng)目管理和綜合工具。Maven提供了開發(fā)人員構(gòu)建一個(gè)完整的生命周期框架。這篇文章主要介紹了windows環(huán)境下java開發(fā)工具maven的安裝,非常不錯(cuò)對大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2020-07-07SpringBoot實(shí)現(xiàn)過濾敏感詞的示例代碼
這篇文章主要為大家詳細(xì)介紹了如何利用SpringBoot實(shí)現(xiàn)過濾敏感詞功能,文中的示例代碼講解詳細(xì),感興趣的小伙伴可以動(dòng)手嘗試一下2022-08-08java天數(shù)計(jì)算函數(shù)(當(dāng)前月天數(shù)、某月總天數(shù)及某月剩余天數(shù))4種方法實(shí)現(xiàn)代碼
日常開發(fā)中會(huì)遇到關(guān)于日期的計(jì)算,比如當(dāng)月的天數(shù)、兩日期之間的天數(shù)、當(dāng)月剩余天數(shù)等等,這篇文章主要給大家介紹了關(guān)于java天數(shù)計(jì)算函數(shù)(當(dāng)前月天數(shù)、某月總天數(shù)及某月剩余天數(shù))4種方法實(shí)現(xiàn)的相關(guān)資料,需要的朋友可以參考下2023-10-10