Làm thế nào chúng ta có thể thực hiện một mẫu variadic rằng, do một loại T
và một danh sách các loại E
, E
... E
N, xác định loại danh sách mà chuyển đổi từ T
thành loại đó, theo độ phân giải quá tải, tốt nhất?variadic mẫu mà quyết định chuyển đổi tốt nhất
void
phải là đầu ra nếu không có chuyển đổi tốt nhất - nói cách khác, khi có sự mơ hồ hoặc T
không thể chuyển đổi thành bất kỳ loại nào trong danh sách.
Lưu ý rằng điều này ngụ ý rằng mẫu của chúng tôi phải thân thiện với SFINAE, tức là không phải là lỗi nghiêm trọng khi không có chuyển đổi tốt nhất nào tồn tại.
sau đây static_assert
s nên thành công:
static_assert(std::is_same< best<int, long, short>, void >{}, "");
static_assert(std::is_same< best<int, long, std::string>, long >{}, "");
static_assert(std::is_same< best<int>, void >{}, "");
(Giả sử, vì đơn giản, đó best
là một mẫu bí danh đề cập đến những mẫu thực tế)
Trường hợp này còn lại không xác định:
static_assert(std::is_same< best<int, int, int>, ???>{}, "");
Hoặc là void
hoặc int
phải được chấp nhận ở đây. (Nếu sau này được chọn sau đó chúng tôi vẫn có thể kiểm tra trong một mẫu wrapper cho dù loại kết quả được chứa hai lần trong danh sách, và nếu nó là, đầu ra void
thay thế).
'(...)' là một chút bực mình: nhiều loại UB được chuyển thành. Làm cho nó 'T &&, ...' và thả nó? – Yakk
@Yakk Nó chỉ đơn thuần là để có một 'int' (để làm cho nó một trận đấu tồi tệ hơn nếu cả hai quá tải' best_conv' ở lại trong tập ứng cử viên), đó là tốt. Tôi có thể làm cho nó 'long' nếu bạn muốn. – Columbo
Ag, tôi thấy: not 'declval ()'. Thiết kế tôi có trong đầu của tôi đã buộc trường hợp 'void' cạnh tranh với các tình trạng quá tải khác trực tiếp hơn (với một' ... 'để đảm bảo nó đi cuối cùng), và tôi chiếu nó vào solutuon khác của bạn. Lấy làm tiếc! – Yakk