4

有一天,我决定开始用普通的 C 语言编写一个视频游戏。
这很有趣,三个月后(我有时没有时间离开工作)我发现自己需要一些物理引擎。
我决定使用 Bullet 物理引擎,因为它似乎是我需要的更好的引擎之一。
然后,我发现 Bullet 并没有真正的 C API,而只有完整的 C++ API。它的 C API 没有维护。
经过一天的诅咒,我将我的项目“转换”为 C++,这是一个大胆的声明,说我对所有堆分配进行了类型转换,我使用 new 和 delete 而不是 malloc 和 free,并在 'extern "C" 中包含了一些定义{ ... }'。
有些人可能会因为我这样做而对我开枪,但我认为没有其他选择可以在 C 中使用性能任务处理的东西,比如这个物理引擎,它只有一个 C++ API。

所以现在,我正在使用 g++ 进行编译,同时仍然主要编写“C”代码。我发现自己不那么开心了,因为代码不再那么纯粹了。
C++ 给了我一些奇怪的错误信息,而我对我经常不喜欢 g++ 解析器的语言没有任何反对。除了我现在可以愉快地将物体相互弹跳之外,我的宠物项目的一些小而纯洁现在已经被遗弃了。

我想知道我是否做对了。我可以征求一些建议吗,我应该继续而不担心为我的“主要”C 代码使用 C++ 编译器吗?是否有其他方法可以在 C 中使用此 API 而不会影响性能或过度维护工作?

4

7 回答 7

5

我想知道我是否做对了。

好吧,您的项目需要一个组件,而不是从头开始重新发明它,您重用了现有的软件。这听起来对我来说确实是正确的。

我可以征求一些建议吗,我应该继续而不担心为我的“主要”C 代码使用 C++ 编译器吗?

你完全不需要担心。C++ 几乎 100% 与 C 兼容。这样做不会受到任何处罚。由于更严格的类型系统,您实际上获得了更好的编译时检查。

是否有其他方法可以在 C 中使用此 API 而不会影响性能或过度维护工作?

不,如果不将代码转换为 C++,就不能在 C 中使用 API。C++ 标识符被破坏:这意味着,即使您准备好从纯 C 使用 C++ API,您也不知道如何引用它们。理论上这是可能的,但实际上不可能。

你的方法是正确的。祝那场比赛好运!

于 2011-02-16T14:19:05.863 回答
4

我认为你过分关注那些不是真正问题的事情。你说有些纯洁已经消失了。嗯,我可以理解这一点。你用 C 编写它,然后意识到你必须使用 C++ 来使用选择的 API,硬塞进去。现在它不再像你的宠物宝宝了。这是一个潜意识问题,而不是编程问题。

我建议你咬紧牙关(哈哈),用 C++ 重写你的项目。然后它会再次纯洁,你会在路上学到很多东西,并且不会觉得你的C-child被鸡奸了。

于 2011-02-16T14:16:13.207 回答
3

根据引擎不同子系统的紧密耦合程度,用不同语言编写引擎的不同部分可能是可行的。

例如,您可以将物理部分分解到导出 C API 的 C++ 模块中,并让应用程序的其余部分留在 C 中。但是,用 C++ 编写系统的中心部分并重构您的应用程序可能更有意义现有的 C 代码到单独的模块中。

于 2011-02-16T14:45:01.193 回答
2

如果您想用 C 编写项目,请用 C 编写并为库制作 C 包装器;看看这个问题以获得一些建议。

否则,用 C++ 重写你的项目;但是请不要在这里和那里用一些 C++ 编写另一个 C 项目,以我的经验,这些项目很快就会变得一团糟(如果你用 C 思维编写代码但调用 C++ 代码,那么奇怪的事情就会在异常发生时开始发生添加到混合物中)。

于 2011-02-16T14:12:43.060 回答
1

不必担心主要编写 C 代码并使用 C++ 编译它。只需采用 new/delete 而不是 malloc/free 就可以了。使用 new 的优点是您不必将结果转换为正确的指针类型(在 C++ 中不允许从 void* 隐式转换为其他指针)并且 new 永远不会返回无效指针。你虽然松了 realloc() 。(不,甚至不要考虑将 new/delete 与 realloc 混合 :))

于 2011-02-16T14:11:31.717 回答
1

将项目保留为“纯 C”的唯一原因是源代码兼容性、工具支持或语言标准(MISRA-C 等)。“我希望它感觉纯净”可能不是一个非常理性的论点。

如果出于这些原因将代码保持为纯 C 很重要,那么您可以用 C++ 编写一个“包装器”DLL(假设是 Windows),它与您的第 3 方 API 进行所有通信。当然,你会得到相当多的开销。

奇怪的错误消息无疑是由 C++ 中更严格的类型造成的,这可能是福也可能是祸,视情况而定。当遇到危险的隐式类型转换(整数提升等)时,C++ 编译器更有可能打你的手指,并且它可能会强制执行更严格的“const 正确性”。但与此同时,它会抱怨 void 指针,这在 C 中被认为是很好的泛型编程,但在 C++ 中是危险的、草率的并且可能是多余的。

于 2011-02-16T15:36:38.210 回答
0

一种选择是使用 LLVM 将 C++ 代码转换为 C。请参阅项目网站上的此常见问题解答:我可以将 C++ 代码转换为 C 代码吗?

于 2011-02-16T14:12:29.157 回答