为什么 gtest 看不到 == 的定义?

drs*_*lks 2 c++ templates googletest

我有一个模板类Matrix

\n\n
    template<typename T>\n    class Matrix {\n        //blah-blah-blah\n        }\n
Run Code Online (Sandbox Code Playgroud)\n\n

以及以下运算符:

\n\n
template<typename T>\nbool operator==(const Matrixes::Matrix<T> &lhs, const Matrixes::Matrix<T> &rhs) {\n    if (lhs.get_cols()!=rhs.get_cols() || lhs.get_rows()!=rhs.get_rows()){\n        return false;\n    }\n    for (int r = 0; r < lhs.get_rows(); ++r) {\n        for (int c = 0; c < lhs.get_cols(); ++c) {\n            if (lhs.get(r, c) != rhs.get(r, c)) {\n                return false;\n            }\n        }\n\n    }\n    return true;\n}\n
Run Code Online (Sandbox Code Playgroud)\n\n

上述运算符是在Matrixes命名空间之外定义的。

\n\n

我有一些测试(我正在使用框架 Google Tests)。但是,如果我写这样的东西:

\n\n
TEST(MatrixOperations, MatrixMultiplicationSimple) {\n    Matrixes::Primitives<int>::VectorMatrix vec1{{{8, 3, 5, 3, 8}, {5, 2, 0, 5, 8}, {0, 3, 8, 8, 1}, {3, 0, 0, 5, 0}, {2, 7, 5, 9, 0}}};\n    Matrixes::Primitives<int>::VectorMatrix vec2{{{3, 1, 7, 2, 9}, {4, 6, 2, 4, 5}, {2, 5, 9, 4, 6}, {5, 3, 3, 1, 2}, {1, 8, 2, 6, 8}}};\n    Matrixes::Matrix<int> vec1m{vec1};\n    Matrixes::Matrix<int> vec2m{vec2};\n    Matrixes::Matrix<int> matrix_out_ref{{{69, 124, 132, 99, 187}, {56, 96, 70, 71, 129}, {69, 90, 104, 58, 87}, {34, 18, 36, 11, 37}, {89, 96, 100, 61, 101}}};\n    Matrixes::Matrix<int> matrix_out_fact = vec1m * vec2m;\n    bool t = matrix_out_fact == matrix_out_ref;\n    EXPECT_EQ(t, true);\n}\n
Run Code Online (Sandbox Code Playgroud)\n\n

一切正常。请注意,我operator==在这里使用“手动”:

\n\n
 bool t = matrix_out_fact == matrix_out_ref;\n EXPECT_EQ(t, true);\n
Run Code Online (Sandbox Code Playgroud)\n\n

但是,如果我不写这两行,而是写如下内容:

\n\n
EXPECT_EQ(matrix_ou_fact, matrix_out_ref);\n
Run Code Online (Sandbox Code Playgroud)\n\n

我收到编译错误:

\n\n
/usr/local/include/gtest/gtest.h:1522:11: error: no match for \xe2\x80\x98operator==\xe2\x80\x99 (operand types are \xe2\x80\x98const Matrixes::Matrix<int>\xe2\x80\x99 and \xe2\x80\x98const Matrixes::Matrix<int>\xe2\x80\x99)\n   if (lhs == rhs) {\n
Run Code Online (Sandbox Code Playgroud)\n\n

为什么看不到gtest的定义operator==

\n\n

谢谢

\n

Sto*_*ica 5

内部比较EXPECT_EQ发生在与您的直接测试用例不同的范围内。它通过参数相关查找(ADL)查找需要调用的运算符函数。由于您的运算符函数与您的类不在同一命名空间中,因此 ADL 不会拾取它。

它可以在您的直接测试用例中工作,因为您可能以适当的顺序包含适当的标头,以便查找运算符不依赖于 ADL。但Gtest框架的实现还得依赖ADL。

所以修复很容易。将您的自定义运算符移至Matrixes命名空间中。它是类的公共接口的一部分,因此无论如何它都属于同一名称空间。