簡體   English   中英

Java ArrayList.set() 方法在 forEach 循環中的意外行為

[英]Unexpected behavior of Java ArrayList.set() method with multiplication in forEach loop

設置初始數組值(沒問題):

import java.util.ArrayList;
public class arraylists {

    public static void main (String[] args) {
        ArrayList<Integer> numbers = new ArrayList<Integer>();
        numbers.add(3);
        numbers.add(1);
        numbers.add(4);
        numbers.add(2);
        System.out.println(numbers.toString());
    }
}

控制台輸出:[3, 1, 4, 2]

嘗試forEach添加(沒問題):

numbers.forEach(number -> {
    numbers.set(numbers.indexOf(number), number + 10);
});
System.out.println(numbers.toString());

控制台輸出:[13、11、14、12]

嘗試forEach乘法:

numbers.forEach(number -> {
    numbers.set(numbers.indexOf(number), number * 2);
});
System.out.println(numbers.toString());

控制台輸出:[6, 4 , 8, 2 ]

我的問題是,為什么乘法循環后的數組在索引 1 處具有值 4,在索引 3 處具有值 2? 它們不應該分別是 1 * 2 = 2 和 2 * 2 = 4 嗎?

我嘗試了上面的代碼,並期望在 forEach 乘法之后得到一個值為 [6, 2, 8, 4] 的數組。 相反,我得到了 [6, 4 , 8, 2 ]。

indexOf返回值第一次出現的索引。 讓我們遍歷循環,看看發生了什么。

  1. 我們從 [3, 1, 4, 2] 開始
  2. 第一個元素是 3。它的索引是 0,所以我們得到 [6, 1, 4, 2]
  3. 第二個元素是1,它的索引是1,所以我們得到[6, 2, 4, 2]
  4. 第三個元素是4,它的索引是2,所以我們得到[6, 2, 8, 2]
  5. 第四個元素是 2,它的第一個索引是 1,所以我們得到 [6, 4, 8, 2]

這不僅是錯誤的(如您所見),還意味着對於每次迭代,您都需要在整個列表(使用indexOf )中搜索一個您應該已經知道它在哪里的值。

使用一個好的舊for循環會更適合這里:

for (int i = 0; i < numbers.size(); ++i) {
    numbers.set(i, numbers.get(i) * 2);
}

您在乘法期間得到不正確的結果,因為在處理最后一個元素時,列表看起來像這樣[6, 2, 8, 2] (索引1處的元素已更改為2 )。 因此, indexOf()返回1 ,而不是3 (正如您可能預期的那樣)。

在這種情況下,當您需要替換列表中的每個元素時,您可以使用 Java 8 方法List.replaceAll()這要方便得多,因為您不需要使用索引撥號:

numbers.replaceAll(number -> number * 2);

System.out.println(numbers);

輸出:

[6, 2, 8, 4]

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM