仅包括操作系统上的某些库
当编写要在Mac,Linux和Windows上编译的应用程序时,管理各种库的最佳方法是什么,这些库需要包含在各种操作系统中。例如,使用glut opengl工具箱需要在每个操作系统上使用不同的include。
解决方案
我从事的几个项目都使用基于autoconf的配置脚本来构建Makefile,因此我们可以使用简单的方法从源代码构建所有这些文件的原因:
./configure make make install
Scons具有一种配置机制,可以完成很多自动工具所需要的工作而没有那么多的复杂性,并且具有很好的可移植性(尽管不如自动工具那样可移植)。
编译器应具有一组预处理器符号,我们可以使用该符号。例如,对于Linux系统上的gcc来说是linux,对于VC ++来说是_WIN32. 如果我们需要更复杂的东西,请查看autoconf,但这对于基于Unix的代码最有效。
我建议我们查看一些较大的OpenSource项目如何处理此问题。请参阅Apache Xerces(旧版本)中的AutoSense.hpp。
如果库在不同平台上提供相同的API,我将创建一个包含所有必要的#ifdef的"代理"包含文件。然后,该"独立于平台"的包含文件将包含在客户端代码中,而不是使用大量读取丑陋的预处理器命令将其弄乱。这些将包含在与平台无关的丑陋和混乱的包含中。
如果不同平台的API不同,则需要创建自己的抽象。
如果我们只需要担心头文件,那么预处理器将满足所有需求。如果要处理不同的源文件以及可能的不同库,则需要一个工具来处理它。
一些选项包括:
- 自动工具
- 骗子
- CMake的
我个人最喜欢的是CMake。 Autotools使用了一个相对容易中断的多阶段过程,对我来说,scons很奇怪。除了makefile,Cmake还将为各种IDE生成项目文件。
也许这是一个解决方案,但是我们是否看过Boost如何处理呢?尽管它们确实有自己的构建系统bjam,它可能处理某些相同的情况,但是它们在没有autoconf的相当多的平台上进行构建。它们还在Windows上做一个很好的自动链接技巧,它会根据MSVC编译器的版本自动选择要链接的库的正确版本。根据最初描述,这听起来像只是对各种平台/编译器进行宏def检查可能会达到目的,但也许问题还有很多事情可以阻止这种情况。
关于宏,有一篇很好的文章。答案之一是如何使用基于OS / COmpiler的条件编译(位于顶部)。
除此以外,自动配置工具的使用是一个不错的补充,但是对于小型项目则不需要,在小型项目中可能更容易显式检测OS,但是对于大型项目,可能需要在许多不同类型的OS上运行,我们也应该探索Branan提到的可用自动配置工具
问题实际上是两个问题合二为一:
1)如何编写我的C ++代码以在正确的平台上包含正确的包含文件?
2)如何编写Makefile在不同平台上工作?
已经回答了C ++代码问题,找到特定于平台的定义,并使用它们来确定我们所处的平台。
Automake或者scons非常复杂,仅当我们打算将代码发布给广大读者时才值得我们花时间。在内部代码的情况下,具有按平台包含的"通用" makefile通常就足够了。对于Windows,我们可以获取Windows的GNU Make(可从此处获得,或者使用nmake并将自己限制为所有平台之间通用的语法的子集。