2012-04-23 49 views
7

Tôi có thể sử dụng mẫu variadic mà không sử dụng tham số mẫu làm tham số chức năng không?Các mẫu biến thể không có tham số chức năng

Khi tôi sử dụng chúng, nó biên dịch:

#include <iostream> 
using namespace std; 

template<class First> 
void print(First first) 
{ 
    cout << 1 << endl; 
} 

template<class First, class ... Rest> 
void print(First first, Rest ...rest) 
{ 
    cout << 1 << endl; 
    print<Rest...>(rest...); 
} 

int main() 
{ 
    print<int,int,int>(1,2,3); 
} 

Nhưng khi tôi không sử dụng chúng, nó không biên dịch và phàn nàn về một sự mơ hồ:

#include <iostream> 
using namespace std; 

template<class First> 
void print() 
{ 
    cout << 1 << endl; 
} 

template<class First, class ... Rest> 
void print() 
{ 
    cout << 1 << endl; 
    print<Rest...>(); 
} 

int main() 
{ 
    print<int,int,int>(); 
} 

Đáng tiếc là các lớp tôi muốn đưa ra dưới dạng tham số mẫu không thể thực hiện được (chúng có các hàm tĩnh được gọi bên trong hàm mẫu). Có cách nào để thực hiện việc này không?

+1

Nếu bạn cần một * unevaluated * biểu hiện của một loại nhất định, bạn có thể sử dụng 'std :: declval ()'. Làm việc cho bất kỳ 'T', có hoặc không có cấu trúc của nó. –

+4

Đối với lý do tại sao phiên bản không đối số không hoạt động: Không có đối số, cả hai quá tải 'in ' và 'in ' đều tốt, trong khi với đối số 'in (3)' là một kết quả tốt hơn so với 'in (3, {}) '(trong đó' {} 'có nghĩa là" không có gì "). Không sử dụng quá tải, như CatPusPus gợi ý, là phương pháp tiêu chuẩn; và kể từ khi bạn không deducing đối số của bạn anyway đó là giải pháp đơn giản nhất. –

+0

Tôi sẽ đăng câu trả lời nhưng không có đã đăng nó. – bames53

Trả lời

20
template<class First> // 1 template parameter 
void print() 
{ 
    cout << 1 << endl; 
} 

#if 0 
template<class First, class ... Rest> // >=1 template parameters -- ambiguity! 
void print() 
{ 
    cout << 1 << endl; 
    print<Rest...>(); 
} 
#endif 

template<class First, class Second, class ... Rest> // >=2 template parameters 
void print() 
{ 
    cout << 1 << endl; 
    print<Second, Rest...>(); 
} 
+1

Bạn có thể loại bỏ mã trùng lặp bằng cách gọi 'print ()' từ phiên bản thấp nhất đó, thay vì lặp lại dòng 'cout'. Tôi nghĩ. –

8

Biến nó thành một loại.

template <typename... Ts> 
struct print_impl; 

template <typename T> 
struct print_impl<T> { 
    static void run() { 
     std::cout << 1 << "\n"; 
    } 
}; 

template <typename T, typename... Ts> 
struct print_impl<T, Ts...> { 
    static void run() { 
     std::cout << 1 << "\n"; 
     print_impl<Ts...>::run(); 
    } 
}; 

template <typename... Ts> 
void print() { 
    print_impl<Ts...>::run(); 
} 

int main() { 
    print<int, int, int>(); 
    return 0; 
} 
+0

Tôi nghĩ sự phức tạp ở đây không xứng đáng. n.m. của giải pháp là đơn giản hơn nhiều. – bames53

Các vấn đề liên quan