Я хочу построить класс, представляющий сопоставление значения типа I
со значением типа O
. Я создал этот интерфейс:
template <typename I, typename O> class Transform {
public:
virtual O transform(I i) = 0;
};
Далее, я хочу разрешить объединение Transform
объектов в своего рода преобразование "в трубу":
template <typename X, typename Y, typename Z> class MergeTransform : public Transform<X, Z> {
private:
Transform<X, Y> *first;
Transform<Y, Z> *second;
public:
MergeTransform(Transform<X, Y> *first, Transform<Y, Z> *second) {
this->first = first;
this->second = second;
}
Z transform(X x) {
return second->transform(first->transform(x));
}
};
Что меня озадачивает На данный момент пытается выяснить, как использовать шаблон для объединения произвольного числа преобразований. Я хотел сделать что-то вроде
template <typename A, typename B, typename C> Transform<A, C> *merge(Transform<A, B> *t1, Transform<B, C> *t2) {
return new MergeTransform(t1, t2);
}
template <typename A, typename... Bs, typename C> Transform<A, C> *merge(/* what should go here? */) {
// ...
}
, но потом я в растерянности от того, как представить список Transform
s из A->B1, B1->B2, B2->...->Bn, Bn->C
во втором merge
методе. Я также подумал о том, чтобы позволить параметрам шаблона быть самими преобразованиями, ie.
/*
* assume A and B are Transforms
*/
template <typename A, typename B> /* some return Transform type here */ *merge(A *a, B *b) {
return new MergeTransform(a, b);
}
template <typename A, typename... Bs, typename C> /* return type */ *merge(A *a, Bs... bs, C *c) {
return merge(merge(a, bs), c);
}
, но не могу определить тип возврата, не зная шаблонных типов A и B Transform
s. Есть ли способ получить доступ к этим значениям? В идеале я мог бы сказать
template <Transform<X, Y> A, Transform<Y, Z> B> Transform<X, Z> *merge(A *a, B *b) {
return new MergeTransform(a, b);
}
template <Transform<W, X> A, Transform<?, ?>... Bs, Transform<Y, Z> C> Transform<W, Z> *merge(A *a, Bs... *bs, C *c) {
return merge(merge(a, bs), c);
}
, когда компилятор выдает ошибку, если расширение merge(a, bs)
не вернуло Transform<X, Y>
. Каков наилучший способ сделать это?