2012-10-16 22 views
6

Tôi muốn viết mẫu vectơ toán học. Tôi có một lớp chấp nhận kiểu và kích cỡ làm đối số mẫu, với rất nhiều phương thức toán học. Bây giờ tôi muốn viết các chuyên ngành trong đó ví dụ như Vector < 3> có x, y, z là các thành viên tham chiếu đến dữ liệu [0..3] tương ứng.C++ - Sử dụng mẫu mặc định làm cơ sở cho chuyên môn

Vấn đề là tôi không biết cách tạo chuyên môn kế thừa mọi thứ từ mẫu mặc định mà không cần tạo lớp cơ sở hoặc viết mọi thứ hai lần.

Cách hiệu quả nhất để thực hiện việc này là gì?

template<class Type, size_t Size> 
class Vector { 
    // stuff 
}; 

template<class T> 
class Vector<3,T>: public Vector { 
    public: 
     T &x, &y, &z; 
     Vector(): Vector<>(), x(data[0]), y(data[1]), z(data[2]){} 
     // and so on 
}; 
+2

Tạo lớp cơ sở là cách tiếp cận điển hình ở đó. –

Trả lời

7

Bằng cách nào đó bạn sẽ có thể lấy được từ việc triển khai mặc định, nhưng bạn là chuyên gia, vậy làm cách nào? nó phải là một phiên bản không chuyên biệt mà bạn có thể lấy được từ nó. Vì vậy, đó là đơn giản:

// Add one extra argument to keep non-specialized version! 
template<class Type, size_t Size, bool Temp = true> 
class Vector { 
    // stuff 
}; 
// And now our specialized version derive from non-specialized version! 
template<class T> 
class Vector<T, 3, true>: public Vector<T, 3, false> { 
    public: 
     T &x, &y, &z; 
     Vector(): Vector<>(), x(data[0]), y(data[1]), z(data[2]){} 
     // and so on 
}; 
+0

Trong khi điều này làm việc độc đáo, có vẻ như một chút clunky (với tôi) để có một tham số mẫu nội bộ trong một giao diện bên ngoài. – Cameron

+0

Người dùng không bao giờ sử dụng tham số mẫu bổ sung này, tất nhiên bạn có một tùy chọn khác mà cả triển khai chuyên biệt lẫn mặc định lấy được từ một lớp cơ sở có chứa thực thi thực tế! nhưng theo tôi thì hơi khó hơn kĩ thuật này! – BigBoss

+0

@BigBoss Nice, cảm ơn bạn. – weltensturm

1

Cân nhắc việc này một cách ít khác nhau, nhưng mục tiêu này sẽ đạt được, Thêm giao diện bên ngoài - Ý tôi là chức năng độc lập X(), Y(), Z():

template<class T, size_t S> 
T& x(Vector<T, S>& obj, typename std::enable_if<(S>=1)>::type* = nullptr) 
{ 
    return obj.data[0]; 
} 

template<class T, size_t S> 
T& y(Vector<T, S>& obj, typename std::enable_if<(S>=2)>::type* = nullptr) 
{ 
    return obj.data[1]; 
} 

template<class T, size_t S> 
T& z(Vector<T, S>& obj, typename std::enable_if<(S>=3)>::type* = nullptr) 
{ 
    return obj.data[2]; 
} 

không có sự khác biệt lớn giữa:

Vector<T, 3>& obj 
return obj.x(); 

Vector<T, 3>& obj 
return x(obj); 

Là phần thưởng - giao diện này hoạt động cho các kích thước phù hợp.