Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/133.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 为什么链接顺序会影响使用宏的测试结果?_C++_Linker_C Preprocessor_Googletest_Googlemock - Fatal编程技术网

C++ 为什么链接顺序会影响使用宏的测试结果?

C++ 为什么链接顺序会影响使用宏的测试结果?,c++,linker,c-preprocessor,googletest,googlemock,C++,Linker,C Preprocessor,Googletest,Googlemock,我正在使用GoogleTest和GoogleMock使用测试驱动开发来编写代码。我正在为谷歌测试写一个小插件。为了确保测试在出现正确消息时会失败,我创建了一个简单的FailureReporter类,我将该类作为子类,并在插件中注入模拟版本以捕获结果并与预期值进行比较 本着TDD极端主义的精神,我还编写了一个测试来确保FailureReporter工作正常。为此,我“替换”了FAIL()。然而,这就是事情变得奇怪的地方。它在一台机器上工作,但在另一台机器上不工作。在查找原因时,我发现可以通过更改链

我正在使用GoogleTest和GoogleMock使用测试驱动开发来编写代码。我正在为谷歌测试写一个小插件。为了确保测试在出现正确消息时会失败,我创建了一个简单的
FailureReporter
类,我将该类作为子类,并在插件中注入模拟版本以捕获结果并与预期值进行比较

本着TDD极端主义的精神,我还编写了一个测试来确保
FailureReporter
工作正常。为此,我“替换”了
FAIL()。然而,这就是事情变得奇怪的地方。它在一台机器上工作,但在另一台机器上不工作。在查找原因时,我发现可以通过更改链接顺序来修复。这似乎很奇怪,因为“修复”是使用宏完成的,我假设它在编译时是硬编码的,链接它不会有什么区别

我发现:链接测试本身不会导致任何问题。仅当在
FailureReporter测试之后链接了另一个测试时,将其与使用FailureReporter模拟版本的测试链接才有效。
为什么会发生这种情况

FailureReporter.hpp:

#ifndef FAILURE_REPORTER_H
#define FAILURE_REPORTER_H

#include "gtest/gtest.h"

class FailureReporter {
public:
    virtual void fail(const char* errorMessage) {
        FAIL() << errorMessage;
    }
};

#endif
DummyTest.cpp

#include "gtest/gtest.h"

#include "MockFailureReporter.hpp"

TEST(DummyTest, dummy) {
    new MockFailureReporter();
    SUCCEED();
}
使用

g++ -c DummyTest.cpp
g++ -c FailureReporterTest.cpp
并将其与

g++ DummyTest.o FailureReporterTest.o -pthread -lgtest -lgmock -lgmock_main
g++ FailureReporterTest.o DummyTest.o -pthread -lgtest -lgmock -lgmock_main
生成失败failMethod测试的a.out可执行文件,同时将其链接到

g++ DummyTest.o FailureReporterTest.o -pthread -lgtest -lgmock -lgmock_main
g++ FailureReporterTest.o DummyTest.o -pthread -lgtest -lgmock -lgmock_main
生成一个a.out可执行文件,该文件成功执行两个测试。为什么?

class FailureReporter {
public:
  virtual void fail(const char* errorMessage) {
    /* code */
创建
FailureReporter::fail
的隐式
inline
实现

内联
函数被导出。如果链接器看到两个名称和类型相同的
内联
函数,它将自动放弃其中一个。如果它们实际上不相同,则说明您的程序格式不正确,不需要进行诊断

当您仅在一个编译单元中重新定义
FAIL()
并将其与其他编译单元链接时,您将得到
FailureReporter::FAIL
的两个定义。它们相互关联,并且未定义行为结果。在您的例子中,两种情况下都会运行其中一个,这取决于链接器选择放弃内联冲突的任意规则。看起来像是“保留我看到的第一个”