Lưu ý: câu trả lời này áp dụng cho Java nhiều hơn là cho C #, vì C # không bật trình lập chỉ mục LinkedLists
, nhưng tôi nghĩ rằng điểm chung vẫn được giữ nguyên.
Nếu list
bạn đang làm việc là a LinkedList
, thì hiệu suất của mã lập chỉ mục ( truy cập kiểu mảng ) kém hơn rất nhiều so với việc sử dụng IEnumerator
from foreach
, cho các danh sách lớn.
Khi bạn truy cập phần tử 10.000 trong một LinkedList
bằng cú pháp của trình lập chỉ mục:, list[10000]
danh sách được liên kết sẽ bắt đầu ở nút đầu và lướt qua Next
-pointer mười nghìn lần, cho đến khi nó đến đúng đối tượng. Rõ ràng, nếu bạn làm điều này trong một vòng lặp, bạn sẽ nhận được:
list[0]; // head
list[1]; // head.Next
list[2]; // head.Next.Next
// etc.
Khi bạn gọi GetEnumerator
(mặc nhiên sử dụng forach
-syntax), bạn sẽ nhận được một IEnumerator
đối tượng có một con trỏ đến nút đầu. Mỗi lần bạn gọi MoveNext
, con trỏ đó được di chuyển đến nút tiếp theo, như sau:
IEnumerator em = list.GetEnumerator(); // Current points at head
em.MoveNext(); // Update Current to .Next
em.MoveNext(); // Update Current to .Next
em.MoveNext(); // Update Current to .Next
// etc.
Như bạn có thể thấy, trong trường hợp của LinkedList
s, phương thức chỉ mục mảng càng ngày càng chậm, bạn lặp lại càng lâu (nó phải đi qua cùng một con trỏ đầu nhiều lần). Trong khi IEnumerable
chỉ hoạt động trong thời gian không đổi.
Tất nhiên, như Jon đã nói, điều này thực sự phụ thuộc vào loại list
, nếu list
không phải là a LinkedList
, mà là một mảng, thì hành vi hoàn toàn khác nhau.