2

我正在使用 gcc 4 和 cmake 为 GNU/Linux 开发应用程序来管理编译过程。我发现当有两个同名但在其他目录和命名空间中的文件时没有问题,如下所示:

.  
|-- gfx  
|   |-- Object.cpp  
|   `-- Object.h  
`-- logic  
    |-- Object.cpp  
    `-- Object.h  

第一个 Object 类在 Gfx 命名空间中,第二个在 Logic 命名空间中。

然后我尝试使用 Visual C++ 2008 Express Edition 编译这个项目。链接器抛出了几个关于 Gfx::Object 类的不存在实现的错误。经过几次检查,我发现:

  • Visual C++ 正在跟踪两个 Object.cpp 文件
  • 当第一个或第二个文件发生更改时,对象单元的重新编译将排队
  • 无论实际修改了哪个文件,它总是只重新编译第二个 Object.cpp

我还发现 Visual C++ 不允许创建两个具有相同名称的类。

有解决方案吗?我真的不想重构相当大的一部分代码。

4

4 回答 4

7

两个 Object.cpp 文件都将编译为 Object.obj。进入同一个目录。换句话说,最后一个编译的将覆盖第一个的 Object.obj。是的,链接器不会对此感到兴奋,因为它两次链接同一个 Object.obj 文件,您将获得多重定义的符号。

修复很简单,右键单击 Object.cpp 文件之一、属性、C/C++、输出文件。将对象文件名从 $(IntDir)\ 更改为 $(IntDir)\$(InputName)2.obj

于 2009-12-28T11:24:36.810 回答
2

问题是VC++2008默认将所有的object文件放到一个输出文件夹中,所以第一个object.obj文件的存在满足了第二个的依赖,所以没有编译;即使是这样,它也会覆盖第一个。

您需要做的是使中间目录设置依赖于正在编译的文件。但是,我尝试将其设置为$(InputDir)和各种其他组合,但无法成功实现有效的配置,尽管它可能是可能的。此处记录了可用的宏。

如果您无法使用“makefile”项目,并使用 make、nmake 或 cmake 或其他方式管理构建,因为您所做的事情根本没有任何问题(即使它是不明智的),只是这样IDE 不容易支持它。

于 2009-12-28T10:32:39.927 回答
1

这已经得到解答,但我还想添加 Visual Studio 2010 会根据我对 Beta 2 的经验,如果发生冲突,会自动将两个 .obj 文件放入不同的目录中。

编辑:哦哦,这是错误的!真正的答案是 CMake 自动为我做这件事。

于 2009-12-28T11:53:23.373 回答
0

公认的解决方案不是最优的,因为它不能扩展。

在 Visual Studio 2010 中,我设置

    Properties -> C/C++ -> Output Files -> Output File Name

    V:\%(Directory)$(PlatformName)_$(ConfigurationName)_%(Filename).obj

假设项目位于驱动器上,则 OBJ 文件最终位于源旁边V(尚不知道是否有宏)。

也不是最优的——但至少我可以轻松地分叉许多源文件的子系统而不会患上腱鞘炎。

顺便说一句:$(InputDir)指的是解决方案/项目目录,在另一个目录会导致同样的问题。

于 2012-08-30T16:13:23.617 回答