【问题标题】:"_main already defined" while using gtest使用 gtest 时“_main 已定义”
【发布时间】:2020-05-06 05:06:28
【问题描述】:

我有一个包含两个项目的解决方案

其中一个是控制台应用程序,另一个是 Google Test 项目

我的项目有一个 .h 文件和一个带有 main() 的 .CPP

我的 gtest 包含一个 .CPP 文件,该文件使用 #include 调用 .h 文件和一个 RUN_ALL_TESTS() 的主函数

我的项目中需要一个 main,但我在 gtest 项目中也需要一个 main,但是有两个 main() 并不能让我成功构建 gtest

有解决办法吗? 抱歉,如果这是一个愚蠢的问题,我不知道如何使用 gtest,因为各个网站不断呈现不同的方式

【问题讨论】:

    标签: c++ visual-studio googletest


    【解决方案1】:

    首先,您应该有一个专用文件main.cpp 用于您的main() 函数,其中不包含任何其他内容。

    例如您的项目结构可能如下所示:

    • 项目1
      • file1.h
      • file1.cpp
      • main.cpp

    我对 gtest 并不熟悉,但通常单元测试框架有一个单独的文件用于 gtest 主函数,例如gtest_main.cpp。测试位于一个或多个文件中,例如 file1test.cpp 等。

    因此,您将编译并链接您的 project1 与 file1.hfile1.cppmain.cpp 以获得可执行文件。

    对于单元测试,您将编译并链接 file1.hfile1.cppfile1test.cppgtest_main.cpp 以获得单元测试可执行文件。

    结构可能是这样的

    • 项目1
      • file1.h
      • file1.cpp
      • main.cpp
    • project1test
      • file1test.cpp
      • gtest_main.cpp

    编辑有关链接的其他信息:

    在 project1test 中,您将包含 file1.h#include "../project1/file1.h"

    要正确链接,请右键单击project1test 项目

    --> 配置属性--> 链接器--> 输入--> 附加依赖--> 添加“..\project1\Debug\file1.obj”

    正如@Alan Birtles 指出的那样,如果你有以下结构会更清楚:

    • project1 库
      • file1.h
      • file1.cpp
    • 项目1申请
      • main.cpp
    • project1test
      • file1test.cpp
      • gtest_main.cpp

    您将获得一个静态/动态库project1library.lib/.dll、一个可执行文件project1application.exe 和一个单元测试可执行文件project1test.exe

    优点是您只需将单元测试项目中的库链接到

    --> 配置属性--> 链接器--> 输入--> 附加依赖--> 添加“..\project1library\Debug\project1library.lib”

    如果您的项目需要多个文件,则不必添加每个 obj 文件,只需添加一个 lib 文件。

    但是,使用 lib、可执行文件和单元测试项目确保所有内容都在更改后正确重建可能会更加困难且容易出错。

    【讨论】:

    • 不要认为这会起作用,将 project1 链接到 project1test 将导致 main 的 2 个定义,您需要 3 个项目,一个用于库,一个用于测试,第三个用于包含 main 的应用程序
    • 如果你只链接 file1.cpp 而不是 main.cpp,它会起作用。但是,您是对的,库、应用程序、测试的不同目录/项目提供了更清晰的分离,但也使其更加复杂。
    • 很抱歉这个菜鸟问题,但是如何在 Visual Studio 2017 中将 gtest_main.cpp 与 file1.h 和 file1.cpp 链接?它们属于不同的项目。
    • 谢谢。我不认为将 main.cpp 与项目的其余部分分开。我使用 file1.h、file1.cpp 和 main.cpp 制作了一个 .lib,为什么它不起作用是有道理的。最后一个疑问,这是完成 C++ 单元测试的标准方式(将主文件与其他文件分开),还是有另一种合适的方式?
    【解决方案2】:

    gtest 的标准用法是用于单元测试。 通常,单元测试不检查 main :)。

    我建议您使用标准的 gtest 主函数(不要定义自定义主函数)。它允许您使用命令行来过滤正在运行的测试。

    如果您不想使用 gtest main,恕我直言,您不应该包含 gtest_main 库。

    【讨论】:

    • 我没有手动包含任何库,我使用的是 VS2017,Google Test 是作为一个包提供的。如果我没有在其中编写带有 RUN_ALL_TESTS() 的 main(),那么测试资源管理器将无法找到我的测试。
    【解决方案3】:

    我使用宏来解决这个问题。我已经定义了一个 TESTING 宏,它在编译单元测试时评估为 true,否则为 false:

    #ifndef TESTING
    // the source main
    int main() {
        ...
    }
    #endif // !TESTING
    

    您也可以稍后将其用于源代码中的“测试”代码。我有时会做什么(不是好的设计 IMO):

    class Klass:
    
    #ifdef TESTING
        friend class KlassUnitTestClass; // allows access to private members in my google test unit class. Disabled when i build sources
    #endif // !TESTING
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2016-12-12
      • 2016-03-09
      • 1970-01-01
      • 2012-09-21
      • 1970-01-01
      • 1970-01-01
      • 2020-08-19
      • 1970-01-01
      相关资源
      最近更新 更多