繁体   English   中英

C ++中的动态绑定示例

[英]Dynamic Binding Example in C++

这段代码是Objective-C [1]中动态绑定的经典示例:

float total = tareWeight;     // start with weight of empty container
int i, n = [self size];       // n = number of members
for (i = 0; i < n; ++i) {     // loop over each member
    id member = [self at:i];  // get next member
    total += [member weight]; // accumulate weight of contents
}
return total;                 // return total weight to caller

因此,作为一名具有该语言经验并在C ++中完成第一步的程序员,我想知道:如果它还支持某种后期绑定,它将如何在C ++中实现?

在这个例子中,我们假设每个成员可以是任何类,但是当然必须实现weight方法。 目前,也可以使用协议等机制,以强制实现兼容(然后将member声明为id<Matter> ),但根本不需要它才能工作。

在C ++中,创建一个具有所谓的虚函数的超类是唯一的选择吗?

编辑

只是为了澄清,上面的代码可以看作是一个容器类方法,它返回其组件的总权重。 你事先不知道容器上会有什么,它可以是任何物体。 您只知道这些对象会响应消息weight


[1]面向对象程序设计,一种进化方法, 第二版,1991年 - Brad J. Cox,Andrew J. Novobilski - 第4章第65页

你最接近C ++的是一个带有虚函数的超类。 虚拟函数如果你真的关心后期绑定,虽然在你的例子中不清楚是否有必要。 权重可以只是超类中可公开访问的数据成员。

C ++中的动态绑定形式严格地在类层次结构中上下。 这允许编译器执行某种级别的检查,而不是将其全部留给运行时系统。 除非你使用不安全的演员阵容。

请注意,您确实在C ++中获得了多重继承,因此您希望能够使用的类只能从此超类继承,但也可以继承其他完全不相关的类。

您的成员变量需要是一个指向可weighable基类的指针。 这样的指针可以引用任何派生的实例。

由于指针会带来内存泄漏风险,因此将其作为智能指针是很聪明的。 C ++ 11有unique_ptr 所以你的班级看起来像

class heavyContainer {
  std::vector<std::unique_ptr<weighable>> members;
 public:
  float total_weight() {
    float result = tareWeight;
    for(auto& member: members)
      result += member->weight();
    return result;
  }
  ...
};

要初始化的任意衍生的实例成员weighable ,你需要堆分配这些对象。 这可能有点棘手,因为没有通用的方法来复制基类指针引用的对象。 一种方法是使插入函数成为模板:

template<class WeighableDerivedObject>
heavyContainer::insert(const WeighableDerivedObject& obj){
  members.push_back(new WeighableDerivedObject(obj));
}

使用C ++ 11移动语义可以使效率更高一些。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM