关于C#:SWIG:在公共功能中使用的私有typedef

SWIG: private typedefs used in public functions

我经常给我的班级一个私有的typedef来引用自己,如下所示:

1
2
3
4
5
6
7
class MyClass {
  private:
    typedef MyClass Self;
  public:
    void DeepCopyFrom(const Self& other);
    ...
};

我现在正在使用SWIGpackage我的C代码,该代码抱怨这样的typedef:

1
error:typedef class MyClass MyClass::Self’ is private

导致此错误的package器代码如下:

1
2
3
4
5
SWIGINTERN PyObject *_wrap_MyClass_DeepCopyFrom(PyObject *SWIGUNUSEDPARM(self), PyObject *args) {
  PyObject *resultobj = 0;
  MyClass *arg1 = (MyClass *) 0 ;
  MyClass::Self *arg2 = 0 ;
  (...)

编译器错误发生在省略号上方的最后一行。

有什么办法告诉SWIG不要使用私有的typedef,而只使用完整的类型名?


我建议保持简单(r):只需删除typedef并改写类名即可。

如果您真的很讨厌,可以告诉SWIG %ignore"损坏的"方法,然后%extend使用package器方法调用真实类的类。除非您要绑定的类和方法的数量相对于您的总代码库而言很小,否则这种治愈方法可能比疾病还差。


默认情况下,

SWIG不会处理任何typedef或声明或private节中的任何内容。因此,它假设(当看到const Self&时)Self是标头中的某种未知类型或其他某种类型,因此将其保留原样并生成其中包含Self的package器代码。问题在于此package器代码是该类外部的函数,并且由于MyClass::Self是私有的,因此编译器会生成错误。我的代码发生了同样的事情:我要做的就是在public部分中声明typedef或将Self重写为MyClass。将typedef更改为public对我来说最有意义。


当您需要不透明类型时,请改用不完整的类(并在实现文件而不是头文件中完成)。

但是在您的特定示例中,它看起来不像应该使用不透明类型。


我很少见过私有的typedef,但是我想在封装方面没有错。但是,如果您有一个使用typedef的公共函数,那么那不是使typedef成为接口的一部分吗?

我想您可以在某些成员函数或私有成员函数接口中使用私有typedef。但是,如果要在公共方法上使用它,则只有typedef也应该是公共的才有意义。

我不知道标准对这个主题说了些什么,但我想这是为数不多的灰色区域之一。我假设它取决于编译器的实现方式,该方式取决于如何在您确定是否可以在公共方法中使用私有typedef(甚至根本可以接受)的类中处理typedef的情况。为了安全起见,我将其公开。

如果您担心公开typedef,请不要在任何公共成员函数的原型中使用它(但仍有可能被某些编译器拒绝)。如果您担心名称冲突,请不要担心,因为无论如何,任何外部代码都必须使用实际的类名来解析作用域。

我认为您可能只是把封装想法带了一点点。