1

Итак, я попал в рассол с шаблонами C++. Предполагая, что я получил иерархию контейнеров типа классов вида:Частичная специализация C++ в инструкции наследования?

template <class T> 
class AContainer{ 
    // ... 
}; 

И через наследование различных контейнеров с различными внутренними представлениями сделаны:

template <class T> 
class AVectorLikeContainer: public AContainer<T>{ 
    // ... 
}; 

И куча иерархий операторных как классы которые имеют вид:

template <template <class T> class C, class T> 
class AnOperator{ 
public: 
    virtual T operator() (const C<T> &c1, const C<T> &c2); 
    // ... 
}; 

Использование наследования и частичные операторы специализации, как они сделаны:

template <class T> 
class AnOperatorForVectorLike: public AnOperator<AvectorLikeContainer, T>{ 
public: 
    virtual T operator() (const AVectorLikeContainer<T> &c1, const AVectorLikeContainer<T> &c2); 
    // ... 
}; 

Теперь, немного позже в проекте, контейнеры вида: были введены

template <class T, std::size_t N> 
class AStaticSizeContainer: public AContainer<T>{ 
    // ... 
}; 

. Очевидно, такой тип разрывает дизайн, поскольку AStaticSizeContainer не соответствует части шаблона шаблона template <class T> class CAnOperator. Путь, чтобы обойти это вводить метафункцию следующим образом:

template <class T, std::size_t N> 
class StaticSizer{ 
public: 
    template <class T1> 
    class SizedStaticContainer: public AStaticSizeContainer<N, T1>{ 
     // ... 
    }; 
}; 

Таким образом, StaticSizer<25>::SizedStaticContainer класс, который соответствует шаблон подписи template <class T> class C. Однако это имеет несколько недостатков. Первым и очевидным является необходимость всегда использовать StaticSize<N>::SizedStaticContainer<T> вместо AStaticSizeContainer<T, N>, даже если T и N являются «известными». Это связано с тем, что они не являются взаимозаменяемыми (один наследуется от другого). Второй недостаток заключается в том, что все конструкторы AStaticSizeContainer должны быть буквально скопированы для StaticSizer::SizedStaticContainer. Я уверен, что есть еще кое-что, что я еще не наткнулся.

Итак, мои вопросы заключаются в следующем:

Есть ли более элегантный способ исправить это время, соответствующую уже выложенной интерфейс? В более широком смысле, можем ли мы уточнить частичную специализацию класса более элегантным способом? В более узких условиях, у нас есть синтаксис, чтобы сказать что-то вроде:

template <class T, std::size_t N> 
class AnOperatorForStaticSize: public AnOperator<AStaticSizeContainer<with N = N>, T>{ 
    // ... 
}; 

где по AStaticSizeContainer<with N = N>, я имею в виду частичной специализации AStaticSizeContainer с N из приведенного выше шаблона.

EDIT 11 C++, по-видимому alias templates-х будет работать, но мне нужна альтернатива в C++ 03.

ответ

1

В начале дня люди C++ экспериментировали с множеством подобных подходов, и ни одна из них не была разработана. Возможно, что, основываясь на опыте последних почти 20 лет, можно было бы разработать более эффективный подход, но, похоже, что общее программирование (введенное в виде STL) обеспечило рабочее решение, в котором нет каких-либо проблем, которые вы описываете. Основная идея решения - fundamental approach to solve problems in computer science: ввести дополнительный уровень косвенности. Вместо привязки структуры к операторам вы должны реализовать операторов с точки зрения обобщенного метода доступа к структуре. В STL структуры - это последовательности, операторы - алгоритмы, а клей между ними - итераторы.

Смежные вопросы