2013-03-16 39 views
104

Trong C++, loại std::map<>::iterator là gì?Ý nghĩa của trình lặp -> thứ hai là gì?

Chúng ta biết rằng một đối tượng it loại std::map<A,B>::iterator có quá tải operator -> mà trả về một std::pair<A,B>*, và rằng std::pair<> có thành viên firstsecond.

Nhưng, hai thành viên này tương ứng với nhau, và tại sao chúng ta phải truy cập giá trị được lưu trữ trong bản đồ là it->second?

+10

Bản đồ 'std :: map' lưu trữ * khóa * và * giá trị * .'map :: iterator.second' dùng để chỉ * giá trị *. –

+0

@AlokSave: Cảm ơn. Nhận xét của bạn đã lưu rất nhiều độc giả đọc hai câu trả lời, rõ ràng, có thể đã bị thu hẹp về độ dài của một tweet. – displayName

Trả lời

163

Tôi chắc chắn bạn biết rằng std::vector<X> lưu trữ toàn bộ một loạt các đối tượng X, phải không? Nhưng nếu bạn có một std::map<X, Y>, những gì nó thực sự lưu trữ là một bó toàn bộ std::pair<const X, Y> s. Đó chính xác là bản đồ - nó kết hợp các khóa và các giá trị liên quan.

Khi bạn lặp qua một số std::map, bạn đang lặp qua tất cả các số std::pair giây này. Khi bạn dereference một trong những iterators, bạn nhận được một std::pair có chứa khóa và giá trị liên quan của nó.

std::map<std::string, int> m = /* fill it */; 
auto it = m.begin(); 

Ở đây, nếu bây giờ bạn làm *it, bạn sẽ nhận được các std::pair cho các phần tử đầu tiên trong bản đồ.

Bây giờ, loại std::pair cung cấp cho bạn quyền truy cập vào các thành phần thông qua hai thành viên: firstsecond. Vì vậy, nếu bạn có std::pair<X, Y> được gọi là p, p.first là đối tượng Xp.second là đối tượng Y.

Vì vậy, bây giờ bạn biết rằng dereferencing một iterator std::map mang đến cho bạn một std::pair, sau đó bạn có thể truy cập phần tử của nó với firstsecond. Ví dụ: (*it).first sẽ cung cấp cho bạn khóa và (*it).second sẽ cung cấp cho bạn giá trị. Chúng tương đương với it->firstit->second.

+2

Tại sao họ không sử dụng [0] và [1] (cho "đầu tiên" và "thứ hai") giống như mọi thứ khác trong lập trình? –

+13

@AdamCross Vì 'toán tử []' phải trả về một kiểu cụ thể nhưng 'first' và' second' có thể có các kiểu khác nhau. Mặt khác, 'std :: tuple' có một hàm trợ giúp đặc biệt' std :: get' để truy cập các phần tử của nó theo chỉ mục. –

+1

Cảm ơn bạn đã trả lời. Điều đó có ý nghĩa bây giờ. –

13

Các loại các yếu tố của một std::map (mà cũng là kiểu của một biểu thức thu được bằng cách dereferencing một iterator của bản đồ đó) mà quan trọng là K và giá trị là Vstd::pair<const K, V> - chìa khóa là const để ngăn cản bạn từ can thiệp với việc sắp xếp nội bộ các giá trị bản đồ.

std::pair<> có hai thành viên có tên firstsecond (xem here), với ý nghĩa khá trực quan. Do đó, đưa ra một iterator i một bản đồ nào đó, khái niệm:

i->first 

Đó là tương đương với:

(*i).first 

Đề cập đến (const) Yếu tố đầu tiên của đối tượng pair trỏ đến bởi trình vòng lặp - tức là nó đề cập đến một khóa trong bản đồ. Thay vào đó, khái niệm:

i->second 

Đó là tương đương với:

(*i).second 

Đề cập đến thứ hai yếu tố của pair - ví dụ: với giá trị tương ứng trong bản đồ.