2016-05-10 13 views
5

Mã của tôi như sauLỗi khi sử dụng java báo cáo foreach

public class Test { 

    public static void main(String[] args) { 
     int count1 = 0, count2 = 0; 
     Test[] test1 = new Test[5]; 
     Test[] test2 = new Test[5]; 
     if (test1 == null || test2 == null) 
      System.out.println("null"); 
     for (int j = 0; j < 3; j++) { 
      for (int i = 0; i < test1.length; i++) { 
       if (test1[i] == null) { 
        test1[i] = new Test(); 
        count1++; 
       } 
      } 
     } 
     for (int j = 0; j < 3; j++) { 
      for (Test test : test2) { 
       if (test == null) { 
        test = new Test(); 
        count2++; 
       } 
      } 
     } 
     System.out.println(count1 + " " + count2); 
    } 
} 

tôi chạy chương trình và tôi thấy đầu ra của nó là 5 15. Điều đó khiến tôi bối rối, tôi không thể hiểu được sự khác nhau giữa việc sử dụng báo cáo và sử dụng báo cáo cho phép. Cảm ơn đã cho tôi một tay.

Trả lời

11

Thay đổi đối với biến lặp trong tuyên bố nâng cao cho làm không ảnh hưởng đến bộ sưu tập cơ bản. Vì vậy, trong khi điều này sẽ thay đổi các mảng:

test[i] = new Test(); // In for loop 

... Đây không:

test = new Test(); // In enhanced for loop 

Vì mảng không được sửa đổi, lần sau khi bạn lặp trên nó, các giá trị là vẫn không, vì vậy bạn sẽ tăng số lượt truy cập của bạn thêm 5 lần. Ditto lần thứ ba bạn lặp qua mảng.

Đạo đức của câu chuyện là: không sử dụng vòng lặp nâng cao nếu bạn muốn sửa đổi nội dung của tập hợp/mảng.

Lưu ý rằng các thay đổi đối với các đối tượng có tham chiếu đã được lưu trữ trong bộ sưu tập/mảng không được tính là sửa đổi tập hợp/mảng. Vì vậy, nếu bạn muốn sẵn có ở đó việc thu thập và đã có một số setName() phương pháp, thì đây:

for (int i = 0; i < test1.length; i++) { 
    test[i].setName("foo"); 
} 

sẽ tương đương với:

for (Test test : test1) { 
    test.setName("foo"); 
} 

Đó là không thay đổi mảng, mà chỉ chứa tham chiếu đến các đối tượng - thay vào đó, nó thay đổi dữ liệu trong các đối tượng đó.

3

Bạn không thể sửa đổi cấu trúc dữ liệu cơ bản bằng cách sử dụng vòng lặp mở rộng ("foreach"), test = new Test(); của bạn không thay đổi mảng.

Các vấn đề liên quan