带有镜像层次结构的c ++双调度

时间:2010-02-28 16:45:27

标签: c++ double-dispatch

以下类层次结构表示抽象资源处理程序和资源层次结构。两者都将接口作为基类。现在假设你编写了一个系统,你可以在这些接口下实现多个特定的资源系统。这只是一个例子。特定的主类创建从东西派生的资源。现在,当创建的资源被传递到基础接口时,它将作为指向基本资源类的指针传递,但我想处理特定资源并可以访问其特定属性。

我知道双重调度,但我不认为它适用于这种情况。我想阻止RTTI和dynamic_casts。你有处理此类案件的建议吗?

class resource;

class main_resource_handler
{
public:
   virtual resource* create_resource() = 0;
   virtual void do_some(resource* st) = 0;
};

class resource
{
};

class specific_resource : public resource
{
public:
    int i;
};

class specific_resource_handler : public main_resource_handler
{
public:
    stuff* create_resource) {
        return new specific_resource);
    }
    void do_some(resource* st) {
        // in here i want to work with specific resource
    }
    void do_some(specific_resource* st) {
        // i want to get here
    }
}

main_resource_handler* handler = new specific_resource_handler();
resource* res = handler->create_resource();
handler->do_some(res); /// here

4 个答案:

答案 0 :(得分:1)

我认为你没有问正确的问题。

要做你想要的,你只需要添加:

template<typename T>
class helper : public main_resource_handler
{
public:
   virtual resource* create_resource() { return new T; }
   virtual void do_some(resource* st) { do_some_specific(static_cast<T*>(st)); }
private:
   virtual void do_some_specific(T* st) = 0;
};

并改变这一点:

class specific_resource_handler : public helper<specific_resource>
{
private:
   virtual void do_some_specific(T* st) { ... }
}

static_cast只有在您可以保证始终在正确类型的处理程序上调用do_some时才是安全的。但是如果你已经知道它是正确的处理程序,那么就不需要进行基类方法调用。所以你想要的是得到某种resource,不知道它的确切类型,并将它传递给适当的处理程序。那太棘手了......

答案 1 :(得分:0)

答案 2 :(得分:0)

我不确定为什么你需要资源和处理程序 - 看起来你正在暴露一个额外的耦合到将被封装的东西。如果create resource刚刚返回了客户端可以直接调用方法的资源,则该问题不存在。

如果您想要安全,请让资源记住创建它的处理程序的地址,然后在do_some(resource* st)中进行检查。如果资源是由当前处理程序创建的,并且处理程序只能创建给定类型的资源,则可以安全地转换它并调用特定函数。虽然如上所述,如果函数只是资源上的虚函数,那么根据定义类型是安全的。

答案 3 :(得分:0)

我想你可能正在寻找这个:

http://www.artima.com/cppsource/cooperative_visitor.html