使用 SWIG 跨 C++ 和 Ruby 的多态性
Posted
技术标签:
【中文标题】使用 SWIG 跨 C++ 和 Ruby 的多态性【英文标题】:Polymorphism across C++ and Ruby using SWIG 【发布时间】:2009-02-14 15:36:40 【问题描述】:我使用 SWIG 将 Ruby 脚本包装在 C++ 库周围。在 Ruby 中,我可以从 C++ 类继承,但不能以多态方式将结果指针传递给 C++ 函数。
这是一个具体的例子。 SWIG 接口文件使用虚函数 sound() 定义基类 Animal:
[animals.i]
%module(directors="1") animals
%
#include "animals.h"
%
// Apply the 'director' feature to a virtual function,
// so that we can override it in Ruby.
%feature("director") Animal::sound;
class Animal
public:
Animal();
virtual ~Animal();
virtual void sound();
;
class Dog : public Animal
public:
Dog();
virtual ~Dog();
virtual void sound();
;
// This function takes an Animal* and calls its virtual function sound().
void kick(Animal*, int);
请注意,我将 SWIG 导向器用于跨语言多态性,但这似乎不起作用。 Ruby 脚本如下所示:
[tst.rb]
require 'animals'
include Animals
dog= Dog.new # Instantiate C++ class
kick(dog, 3) # Kick the dog 3 times => It barks 3 times.
# So far so good.
class Cat < Animal # Inherit from a C++ class
def initialize
puts "Creating new cat"
end
def sound
puts "Meow"
end
end
cat= Cat.new # Instantiate Ruby class
kick(cat, 9) # This does not fly.
脚本的最后一行产生了这个错误:
Expected argument 0 of type Animal *, but got Cat #<Cat:0xb7d621c8>
所以不知何故 SWIG 不允许我将 Ruby 对象视为指向动物的指针。有什么想法吗?
【问题讨论】:
【参考方案1】:我从 swig-user 邮件列表中的 Tobias Grimm 那里得到了我的问题的解决方案。 问题的第一部分是 SWIG 的误导性错误消息。 该消息似乎表明我将错误类型的指针传递给我的 C++ 功能,但事实并非如此。如果您检查异常的类 在 Ruby 中,它是 ObjectPreviousDeleted,这意味着底层的 C 结构指针 我的 Cat 课程为 NULL。所以真正的问题是指针是NULL, 并不是它的类型不对。
指针为 NULL,因为我只是忘记在 Cat 的 initialize() 中调用“super” 方法。这样,随着 Cat 的创建,没有分配底层 C 结构, 因为 Animal 构造函数永远不会被调用。 忘记调用 'super' 是一个非常常见的 Ruby 初学者的错误,尤其是 对于像我这样来自 C++,习惯于自动构造函数链接的人。
所以我所要做的就是添加对“super”的调用:
class Cat < Animal # Inherit from a C++ class
def initialize
puts "Creating new cat"
super()
end
def sound
puts "Meow"
end
end
现在可以正常工作了。谢谢,托比亚斯。
【讨论】:
谢谢你!真的,如果super()
没有从覆盖的 initialize()
方法中调用,那么在将 Ruby 传递给 C++ 时会出现错误 ObjectPreviouslyDeleted
。【参考方案2】:
我相信您需要定义一个 helper function 来返回指向您的实例的指针。 我只使用了 fopen 的指针,所以我不知道这是否真的有效,或者我是否还缺少其他东西。 祝你好运!
【讨论】:
以上是关于使用 SWIG 跨 C++ 和 Ruby 的多态性的主要内容,如果未能解决你的问题,请参考以下文章