我尝试为一些C++类(可能使用模板)生成Perl包,但遇到了一个奇怪的问题,派生类对象无法调用基类方法,在C++类中公开继承的方法。
阅读swig 4.0手册后,我成功设置了我的类(包括模板类)并正确地编译它们,没有错误。我知道如何对它们进行排序以及如何分离模块,以便正确地编译它们。
不知何故,当在perl中使用派生类对象时,它无法访问基类方法 - 这就是我需要帮助的地方。如果我查看对象转储(使用
我尝试将其显式链接到DerivedClass.so文件,但没有成功。
请注意,我能够使相同的程序工作,但没有使用模板。在我的Perl脚本中,我能够从派生类对象执行基类方法。
有人可以指导我进一步调查的方向吗?目前,我无法在互联网上找到与我的用例相关的任何相关信息,即无法在Perl中执行基类方法。
如果您对此问题感兴趣,请在下面找到用于执行此小测试的文件:
Perl程序引发未定义的符号错误:
阅读swig 4.0手册后,我成功设置了我的类(包括模板类)并正确地编译它们,没有错误。我知道如何对它们进行排序以及如何分离模块,以便正确地编译它们。
不知何故,当在perl中使用派生类对象时,它无法访问基类方法 - 这就是我需要帮助的地方。如果我查看对象转储(使用
objdump -t
命令),我会发现base_hello()方法仍然未定义,但似乎无法弄清楚原因?我尝试将其显式链接到DerivedClass.so文件,但没有成功。
请注意,我能够使相同的程序工作,但没有使用模板。在我的Perl脚本中,我能够从派生类对象执行基类方法。
有人可以指导我进一步调查的方向吗?目前,我无法在互联网上找到与我的用例相关的任何相关信息,即无法在Perl中执行基类方法。
如果您对此问题感兴趣,请在下面找到用于执行此小测试的文件:
Perl程序引发未定义的符号错误:
20190901 03:25 [compuser@lenovoe470:template-base-class]$ perl testDerivedClass.pl
Hello from derived class
perl: symbol lookup error: /home/compuser/mystuff/study/ace/swig-with-ace/template-base-class/BaseClass.so: undefined symbol: _ZN9BaseClassIiE10base_helloEi
20190901 03:25 [compuser@lenovoe470:template-base-class]$
Baseclass.i
%module BaseClass
%{
#include "BaseClass.h"
%}
%include "BaseClass.h"
%template(intBaseClass) BaseClass< int > ;
Derivedclass.i
%module DerivedClass
%import "BaseClass.i"
%{
#include "DerivedClass.h"
%}
%include "DerivedClass.h"
Baseclass.h
#ifndef BC__
#define BC__
#include <iostream>
template <class T>
class BaseClass {
public:
void base_hello(T value);
};
#endif /* BC__ */
Baseclass.cpp
#include "BaseClass.h"
template <class T>
void BaseClass<T>::base_hello(T value) {
std::cerr << "Hello from base class: " << value << "\n";
}
Derivedclass.h
#ifndef __DC_
#define __DC_
#include "BaseClass.h"
class DerivedClass : public BaseClass <int> {
public:
void derived_hello();
};
#endif /* __DC_ */
Derivedclass.cpp
#include "DerivedClass.h"
void DerivedClass::derived_hello() {
std::cerr << "Hello from derived class\n";
}
testDerivedClass.pl
#!/usr/bin/env perl
use strict;
use warnings;
use Data::Dumper;
use DerivedClass;
my $obj = new DerivedClass::DerivedClass();
$obj->derived_hello();
$obj->base_hello();
__END__
更新: 添加编译命令
#### For Base Class
/usr/local/bin/swig -c++ -perl5 BaseClass.i
g++ -std=c++11 -c -fPIC `perl -MConfig -e 'print join(" ", @Config{qw(ccflags optimize cccdlflags)}, "-I$Config{archlib}/CORE")'` -D_GNU_SOURCE -L. BaseClass.cpp BaseClass_wrap.cxx
g++ -std=c++11 -lstdc++ `perl -MConfig -e 'print $Config{lddlflags}'` -L. BaseClass.o BaseClass_wrap.o -o BaseClass.so
#### For Derived Class
/usr/local/bin/swig -c++ -perl5 DerivedClass.i
g++ -std=c++11 -c -fPIC `perl -MConfig -e 'print join(" ", @Config{qw(ccflags optimize cccdlflags)}, "-I$Config{archlib}/CORE")'` -D_GNU_SOURCE -L. DerivedClass.cpp DerivedClass_wrap.cxx
g++ -std=c++11 -lstdc++ `perl -MConfig -e 'print $Config{lddlflags}'` -L. DerivedClass.o DerivedClass_wrap.o -o DerivedClass.so
testDerivedClass.pl
,只需将当前目录添加到包含路径中:perl -I. testDerivedClass.pl
。它不会产生错误undefined symbol: _ZN9BaseClassIiE10base_helloEi
。但是,如果您使用gcc
而不是g++
来编译扩展程序,则可能会出现此类错误。 - Håkon Hægland