【问题标题】:typedef and struct namespaces in C vs C++C 与 C++ 中的 typedef 和 struct 命名空间
【发布时间】:2012-04-20 05:07:44
【问题描述】:

我正在尝试在一些新的 C++ 中使用一些旧的 C 库。

该库的头文件使用 D. Hanson 的 "C Interfaces and Implementations" implementation-hiding idiom of:

#define T MyAST 

typedef struct T *T;

据我所知,这可以用 C 编译,因为在 C 中,结构名称和 typedef 名称位于不同的命名空间中,但它不能用 C++ (extern "C" { #include "MyAST.h" }) 编译,这显然是因为 typedef 和 struct 名称位于相同的命名空间中。

conflicting declaration 'typedef struct MyAST* MyAST'

我认为我注定将 struct def 移动到标题中并放弃使用该技术,但我真的不想(这个成语用于很多代码,有些是我的,有些不是)并认为我会在这里查看是否有人有任何见解。

PS:如果你不知道这个习语,它可以让你将结构定义保留在实现的 C 文件中,然后接口的用户 (MyAST.h) 无法进入结构,他们必须使用你的函数在实现中。

【问题讨论】:

  • 只是出于好奇:您为什么要这样做?
  • @Philip:大概是因为没有库具有可满足 OP 需要的合理 API。或者,如果您的意思是,您为什么要这样做疯狂的 typedef:这是为了在每个声明中为库用户节省一点输入。有了这个废话,你只需要写MyAST myAST;;而更健全的 API 可能会迫使您将手指戴在骨头上打字struct MyAST * myAST;
  • @Mike:你让我好奇。请看stackoverflow.com/questions/10243149/…

标签: c++ c compiler-construction struct typedef


【解决方案1】:

老实说,如果这里的唯一目的是使用一些旧库(我们假设不会更新),我会在您的 C++ 和旧库之间创建一个粘合层。只需编写少量用 C 编译的包装器代码以使用旧库,并为新的 C++ 代码提供用 C++ 编译的 C 接口。

同名意味着两个不同的东西,只会在未来的维护者中造成混淆,所以我会尝试将接口代码隔离到几个源文件中。

最后,虽然我很感激希望在某些时候将接口与实现分开,但您必须相信您的代码用户不会公然违反库的条件,并且只需以明显的方式对其进行编码,而不是偏执的长度隐藏结构定义。

【讨论】:

    猜你喜欢
    • 2011-05-04
    • 1970-01-01
    • 1970-01-01
    • 2013-07-17
    • 1970-01-01
    • 1970-01-01
    • 2017-05-13
    • 1970-01-01
    • 2015-06-26
    相关资源
    最近更新 更多