Có nhiều quá tải std::get
, trong đó, ngoài ra, mỗi mẫu là một mẫu hàm, do đó trình biên dịch không thể cho biết bạn muốn trang web nào yêu cầu địa chỉ của một trong số chúng. Nếu bạn nhấn mạnh vào việc sử dụng std::get
, bạn sẽ cần phải sử dụng static_cast
:
transform(mss.begin(), mss.end(), back_inserter(vs),
static_cast<const map<string, string>::key_type&
(*)(map<string, string>::value_type&)>(std::get<0>)
);
nào sẽ làm việc miễn là gõ vào static_cast
phù hợp với tuyên bố của chuyên môn hóa một chức năng có thể sửa mẫu cho làm đối số. Ngoài ra, bạn không nên cố gắng xác định rõ ràng các đối số mẫu của các mẫu chức năng như get<0, string, string>
v.v. - đây là cơ chế khấu trừ đối số khuôn mẫu cho cái gì. Cú pháp không chỉ xấu xí, mà còn có thể có các tình trạng quá tải khác được thêm vào trong tương lai phá vỡ quá trình biên dịch của bạn.
Một lựa chọn tốt hơn nhiều là sử dụng một biểu thức lambda :
transform(mss.begin(), mss.end(), back_inserter(vs),
[](map<string, string>::value_type& p){ return p.first; });
hoặc một generic biểu thức lambda (C++ 14):
transform(mss.begin(), mss.end(), back_inserter(vs),
[](auto& p){ return p.first; }); // or `return std::get<0>(p);`
hoặc std::mem_fn
mà liên kết với nó đối số cho một con trỏ cho một thành viên dữ liệu hoặc một hàm thành viên:
#include <functional>
transform(mss.begin(), mss.end(), back_inserter(vs),
mem_fn(&map<string, string>::value_type::first));
Cảm ơn. Tôi đã hy vọng có thể giữ được siêu ngắn gọn 'get <0>' nhưng ... nó không có nghĩa là. Ồ, tốt. – screwnut