Trong khi thực hiện lập trình mẫu variadic trong C++ 11 trên GCC, thỉnh thoảng tôi nhận được lỗi có nội dung "Rất tiếc, chưa triển khai: không thể mở rộng 'Số nhận dạng ...' thành danh sách tăng độ dài cố định". Nếu tôi xóa "..." trong mã thì tôi gặp lỗi khác: "lỗi: các gói tham số không được mở rộng bằng '...'".Lỗi GCC với mẫu variadic: "Rất tiếc, chưa triển khai: không thể mở rộng 'Số nhận dạng ...' thành danh sách đối số có độ dài cố định"
Vì vậy, nếu tôi có "..." trong, GCC gọi là một lỗi, và nếu tôi lấy "..." ra, GCC gọi đó là một lỗi quá. Cách duy nhất tôi có thể giải quyết vấn đề này là viết lại hoàn toàn metaprogram mẫu từ đầu bằng cách sử dụng một cách tiếp cận khác, và (với may mắn) cuối cùng tôi đã tìm ra mã không gây ra lỗi. Nhưng tôi thực sự muốn biết những gì tôi đã làm sai. Mặc dù Googling cho nó và mặc dù thử nghiệm nhiều, tôi không thể pin xuống những gì nó là tôi đang làm khác nhau giữa mã mẫu variadic mà sản xuất lỗi này, và mã mà không có lỗi.
Từ ngữ của thông báo lỗi dường như ngụ ý rằng mã phải hoạt động theo tiêu chuẩn C++ 11, nhưng GCC chưa hỗ trợ nó. Hoặc có lẽ nó là một lỗi trình biên dịch?
Đây là một số mã tạo lỗi. Lưu ý: Tôi không cần bạn phải viết một thực hiện đúng đối với tôi, nhưng thay vì chỉ để chỉ ra những gì là về mã của tôi đó gây ra lỗi cụ thể này
// Used as a container for a set of types.
template <typename... Types> struct TypePack
{
// Given a TypePack<T1, T2, T3> and T=T4, returns TypePack<T1, T2, T3, T4>
template <typename T>
struct Add
{
typedef TypePack<Types..., T> type;
};
};
// Takes the set (First, Others...) and, while N > 0, adds (First) to TPack.
// TPack is a TypePack containing between 0 and N-1 types.
template <int N, typename TPack, typename First, typename... Others>
struct TypePackFirstN
{
// sorry, unimplemented: cannot expand ‘Others ...’ into a fixed-length argument list
typedef typename TypePackFirstN<N-1, typename TPack::template Add<First>::type, Others...>::type type;
};
// The stop condition for TypePackFirstN: when N is 0, return the TypePack that has been built up.
template <typename TPack, typename... Others>
struct TypePackFirstN<0, TPack, Others...> //sorry, unimplemented: cannot expand ‘Others ...’ into a fixed-length argument list
{
typedef TPack type;
};
EDIT: tôi đã nhận thấy trong khi đó một mẫu instantiation phần trông giống như không phải chịu các lỗi:
template <typename... T>
struct SomeStruct<1, 2, 3, T...> {};
Viết lại nó như thế này không tạo ra một lỗi:
template <typename... T>
struct SomeStruct<1, 2, 3, TypePack<T...>> {};
Có vẻ như bạn có thể khai báo các tham số cho các chuyên môn từng phần là variadic; tức là dòng này là OK:
template <typename... T>
Nhưng bạn có thể không thực sự sử dụng những gói thông số trong chuyên môn, tức là phần này không phải là OK:
SomeStruct<1, 2, 3, T...>
Thực tế là bạn có thể làm cho nó hoạt động nếu bạn quấn gói trong một số loại khác, tức là như thế này:
SomeStruct<1, 2, 3, TypePack<T...>>
với tôi ngụ ý rằng khai của tham số variadic đến một chuyên môn mẫu từng phần đã thành công và bạn không thể sử dụng nó trực tiếp. bất cứ ai có thể xác nhận điều này?
Nó có thể hoạt động ngay bây giờ với 'clang 3.2' – alfC