4

我想做这样的事情:

template<class T>
class BaseSubscriber {};

template<class T>
class BasePublisher
{
    // not working : invalid use of template-name 'BaseSubscriber' without an argument list
    typedef BaseSubscriber SubscriberType;

    // compiling
    typedef BaseSubscriber<T> SubscriberTypeT;
};


template< template<class T> class Subscriber, class Data >
class ClassA:
    public Subscriber<Data> 
{
};

template< template<class T> class Publisher, class Data >
class ClassB:
    public Publisher<Data>  
{
    // Ok, but I want that the type "BaseSubscriber" depends on the template parameter Publisher
    void method1(ClassA<BaseSubscriber, Data>&);


    // I want something like that. But how to define SubscriberType ?
    void method2(ClassA<Publisher<Data>::SubscriberType, Data>&);
    // or (SubscriberType only depends on the Publisher, nor on the Data)
    void method2(ClassA<Publisher::SubscriberType, Data>&);


    // Error : template argument is invalid
    void method3(ClassA<Publisher::SubscriberTypeT, Data>&);
};

是否可以定义一些SubscriberType可用于classA模板参数的内容?或者有什么解决办法吗?

如果可能的话,我想保留classA原型。我不想改变它

template<class TSubscriber > classA {};

而且我不能使用 C++11。非常感谢你的回答。

4

3 回答 3

3

当您说:

// I want something like that. But how to define SubscriberType ?
void method2(ClassA<Publisher::SubscriberType>);

作为Publisher模板,但您没有向它传递任何参数。

无论如何,这里有一些选项:

在 C++11 中,您可以使用模板别名:

template<class T>
class BasePublisher
{
    template<typename U>
    using SubscriberType = BaseSubscriber<U>;
};

您还可以使用嵌套类:

template<class T>
class BaseSubscriber {};

template<class T>
class BasePublisher
{
    template<class U>
    class BaseSubscriber {};
};

或更改ClassA为使用type会员:

template<class T>
class BasePublisher
{
    template<class U>
    struct SubscriberType {
        typedef BaseSubscriber<U> type;
    };
};

template< template<class T> class SubscriberT >
class ClassA {
    typedef typename SubscriberT::type Subscriber;
};

或者,如果您不需要别名,有时继承会起作用:

template<class T>
class BasePublisher
{
    template<class U>
    struct SubscriberType : BaseSubscriber<U> {};
};
于 2012-11-07T10:03:28.737 回答
1

C++03 中不允许使用模板别名,尽管它们在 C++11 中。

你的目标是能够做到:

typename BaseSubscriber<A>::SubscriberType<B>

在 C++03 中,您应该使用嵌套类:

template< typename T > struct BasePublisher
{
   template< typename U > struct Subscriber
   {
       typedef BaseSubcriber<U> type;
   };
};

现在你可以做 typename BasePublisher::Subscriber::type;

在 C++11 中,语法为:

template < typename T > struct BasePublisher
{
   template< typename U > using SubscriberType = BaseSubscriber<U>;
};

还没有很多编译器支持它。虽然你不能做 typename typename 它可能需要另一个 typedef 。

于 2012-11-07T10:02:27.877 回答
0

如果我理解正确,您希望ClassA获得 的实例化BaseSubscriber,例如BaseSubscriber<my_tag>ClassB的实例化BasePublisher。这是对的吗?

如果您的答案是肯定的,那么为什么您将and的template参数声明为模板,您不想在or中对它做任何事情,所以它应该是一个类而不是模板类:ClassAClassBClassAClassB

template<class T>
class BasePublisher
{
    // compiling
    typedef BaseSubscriber<T> SubscriberTypeT;
};
template< class SubscriberT > class ClassA : SubscriberT {};
template< class PublisherT >
class ClassB : PublisherT {
    void method1( ClassA<typename PublisherT::SubscriberTypeT> );
};
于 2012-11-07T10:13:20.690 回答