好的,昨天我发布了几乎相同的问题here
,但我无法根据自己的需要修改答案(有效)...我不想弄乱另一个主题,所以我开始了一个新的话题。

所以,我有2个(实际上大约是15个)结构,它们可以组成一个对象

class MyBase{};

template <typename Super, typename T1, typename T2>
struct A : public Super
{
    void doStuffA() { cout<<"doing something in A"; }
};

template <typename Super, typename T1, typename T2>
struct B : public Super
{
    void doStuffB() { cout<<"doing something in B"; }
};


然后我有:

template <typename ComposedType, typename T1, typename T2>
class Combined
{
    ComposedType m_cT;
public:
    Combined(const ComposedType & c) : m_cT(c) { }

    typedef A<null, T1, T2> anull;
    typedef B<null, T1, T2> bnull;

    void update()
    {
        typedef typename split<ComposedType>::Ct Ct;
        typedef typename split<ComposedType>::At At;

        //this I want
        if( composed of A )
            m_cT.doStuffA();

        if( composed of B )
            m_cT.doStuffB();
    }
};


我想像这样使用它:

int main()
{
    typedef A<B<MyBase,int,int>,int,int> ComposedType1;
    typedef B<MyBase,int,int> ComposedType2;

    ComposedType1 ct1;
    ComposedType2 ct2;

    Combined<ComposedType1, int, int> cb1(ct1);
    cb1.update();

    Combined<ComposedType2, int, int> cb2(ct2);
    cb2.update();
}


(int仅出于示例目的)

所以我有一些模板魔术:

struct null{};

template<typename>
struct split
{
    typedef null Ct;
    typedef null At;
};

template<template<typename> class C, typename T>
struct split<C<T> >
{
    typedef C<null> Ct; //class template
    typedef T      At;  //argument type
};

template<template<typename> class C>
struct split<C<MyBase> >
{
    typedef C<null> Ct; //class template
    typedef MyBase   At;  //argument type
};


但我不能使它工作:(

我知道有很多代码,但这实际上是最小的示例……我已将此代码发布到ideone,以使其更易于阅读。

谢谢!

编辑:(在评论中提问)

我正在构建用于AI的系统,并想解决编译中的许多问题
尽我所能。在这种情况下,我正在构建运动行为系统。
 我的代码提供了许多类型的行为,例如“转到点”,“逃避”,
 “避免障碍”等。此行为在上面的示例中
每个行为都有类似“ performBehavior”的方法
及其返回类型可以与其他“ performBehavior”组合。

所以我想在编译时将特定的行为放在一起。例如。只是A或A + C + D + F等...

然后在我的更新中执行以下操作:

如果行为由“转到点”组成,则比“ performBehaviorGoTo”

如果行为由“避开”组成,而不是“ performBehaviorEvade”

...

这是一个非常简短的解释,但希望我能指出我的意思

最佳答案

您可以使用函数重载来实现:

template <typename Super, typename T1, typename T2>
void doStuff(A<Super, T1, T2>& a) { a.doStaffA(); }

template <typename Super, typename T1, typename T2>
void doStuff(B<Super, T1, T2>& b) { b.doStaffB(); }


接着:

// ...
void update()
{
    //this I want
    //if( composed of A )
    //    m_cT.doStuffA();
    //if( composed of B )
    //    m_cT.doStuffB();

    doStuff(m_cT);
}


不清楚是否要链接A<B<...> >的调用。如果这样做,则将执行以下操作:

template <class T>
void doStuff(T&) { /* do nothing */ }

template <typename Super, typename T1, typename T2>
void doStuff(A<Super, T1, T2>& a) {
    a.doStaffA();
    doStuff(static_cast<Super&>(a));
}

template <typename Super, typename T1, typename T2>
void doStuff(B<Super, T1, T2>& b) {
    b.doStaffB();
    doStuff(static_cast<Super&>(b));
}

关于c++ - 如何查找对象由哪些类型组成?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/7013286/

10-09 13:35