[Google Test]- Google Test Ubuntu 完整验证指南

Google Test Ubuntu 完整验证指南

一、环境安装

1.1 安装依赖

sudo apt-get update

sudo apt-get install -y build-essential cmake libgtest-dev git

1.2 编译 gtest 库(重要!)

libgtest-dev 只安装源码,需要手动编译:

cd /usr/src/gtest

sudo cmake CMakeLists.txt

sudo make

sudo cp *.a /usr/lib

或者使用 CMake FetchContent(推荐,无需系统安装)

二、项目结构

gtest_template_test/

├── CMakeLists.txt

├── include/

│ └── calculator.hpp # 被测试的模板类

├── src/

│ └── main.cpp # 可选的主程序

└── tests/

└── test_calculator.cpp # 测试代码

三、被测试的模板类(非虚接口)

复制代码

include/calculator.hpp

ifndef CALCULATOR_HPP

define CALCULATOR_HPP

include

include

// 模板类 - 非虚接口(编译时多态)

template

class Calculator {

public:

// 非虚成员函数

T add(T a, T b) const {

return a + b;

}

复制代码
T subtract(T a, T b) const {
    return a - b;
}

T multiply(T a, T b) const {
    return a * b;
}

T divide(T a, T b) const {
    if (b == T{}) {
        throw std::invalid_argument("Division by zero");
    }
    return a / b;
}

// 模板成员函数
template
T accumulate(const U* begin, const U* end, T init) const {
    T result = init;
    for (const U* ptr = begin; ptr != end; ++ptr) {
        result = add(result, static_cast(*ptr));
    }
    return result;
}

};

// 模板特化示例

template

class Calculator {

public:

const char* add(const char* a, const char* b) const {

return "string_concat_not_supported";

}

};

endif // CALCULATOR_HPP

四、测试代码

tests/test_calculator.cpp

include

include "calculator.hpp"

include

include

include

// ============================================

// 测试夹具(Test Fixture)- 用于模板测试

// ============================================

template

class CalculatorTest : public ::testing::Test {

protected:

Calculator calc;

复制代码
void SetUp() override {
    // 每个测试前执行
}

void TearDown() override {
    // 每个测试后执行
}

};

// 定义测试类型列表

using TestTypes = ::testing::Types;

TYPED_TEST_SUITE(CalculatorTest, TestTypes);

// ============================================

// 类型化测试(Typed Tests)

// ============================================

TYPED_TEST(CalculatorTest, AddTest) {

TypeParam result = this->calc.add(TypeParam{2}, TypeParam{3});

EXPECT_EQ(TypeParam{5}, result);

}

TYPED_TEST(CalculatorTest, SubtractTest) {

TypeParam result = this->calc.subtract(TypeParam{10}, TypeParam{4});

EXPECT_EQ(TypeParam{6}, result);

}

TYPED_TEST(CalculatorTest, MultiplyTest) {

TypeParam result = this->calc.multiply(TypeParam{3}, TypeParam{4});

EXPECT_EQ(TypeParam{12}, result);

}

TYPED_TEST(CalculatorTest, DivideTest) {

TypeParam result = this->calc.divide(TypeParam{20}, TypeParam{4});

EXPECT_EQ(TypeParam{5}, result);

}

TYPED_TEST(CalculatorTest, DivideByZeroThrows) {

EXPECT_THROW(this->calc.divide(TypeParam{10}, TypeParam{0}),

std::invalid_argument);

}

// ============================================

// 非模板类的普通测试

// ============================================

TEST(CalculatorTest, AccumulateFunction) {

Calculator calc;

std::vector numbers = {1, 2, 3, 4, 5};

int result = calc.accumulate(numbers.data(),

numbers.data() + numbers.size(),

0);

EXPECT_EQ(15, result);

}

// ============================================

// 参数化测试(Parameterized Tests)

// ============================================

class ParameterizedCalcTest : public ::testing::TestWithParam> {

protected:

Calculator calc;

};

TEST_P(ParameterizedCalcTest, AddParameterized) {

auto [a, b, expected] = GetParam();

EXPECT_EQ(expected, calc.add(a, b));

}

INSTANTIATE_TEST_SUITE_P(

AdditionCases,

ParameterizedCalcTest,

::testing::Values(

std::make_tuple(1, 2, 3),

std::make_tuple(10, 20, 30),

std::make_tuple(-5, 5, 0),

std::make_tuple(100, 200, 300)

)

);

// ============================================

// 浮点数比较测试

// ============================================

TEST(FloatCalculatorTest, FloatingPointComparison) {

Calculator calc;

double result = calc.divide(1.0, 3.0);

EXPECT_DOUBLE_EQ(0.3333333333333333, result);

EXPECT_NEAR(0.3333, result, 0.0001); // 允许误差

}

// ============================================

// 死亡测试(Death Test)- 验证程序崩溃

// ============================================

TEST(DeathTest, DivisionByZeroCrash) {

// 注意:死亡测试需要特殊编译标志

Calculator calc;

// EXPECT_DEATH(calc.divide(10, 0), ".*"); // 需要启用

}

// ============================================

// Main 函数

// ============================================

int main(int argc, char **argv) {

::testing::InitGoogleTest(&argc, argv);

return RUN_ALL_TESTS();

}

五、CMakeLists.txt 配置

CMakeLists.txt

cmake_minimum_required(VERSION 3.14)

project(GTestTemplateTest LANGUAGES CXX)

C++ 标准

set(CMAKE_CXX_STANDARD 17)

set(CMAKE_CXX_STANDARD_REQUIRED ON)

方法1: 使用系统安装的 gtest

find_package(GTest REQUIRED)

include_directories({GTEST_INCLUDE_DIRS})

方法2: 使用 FetchContent(推荐,无需系统安装)

include(FetchContent)

FetchContent_Declare(

googletest

GIT_REPOSITORY https://github.com/google/googletest.git

GIT_TAG v1.14.0

)

FetchContent_MakeAvailable(googletest)

包含目录

include_directories({CMAKE_SOURCE_DIR}/include)

测试可执行文件

add_executable(run_tests tests/test_calculator.cpp)

链接 gtest

target_link_libraries(run_tests

GTest::gtest

GTest::gtest_main

pthread

)

启用测试

enable_testing()

add_test(NAME TemplateTests COMMAND run_tests)

编译选项(启用死亡测试需要)

target_compile_definitions(run_tests PRIVATE GTEST_HAS_DEATH_TEST=1)

复制代码

六、编译与运行

6.1 创建构建目录并编译

mkdir build && cd build

cmake ...

make -j$(nproc)

6.2 运行测试

运行所有测试

./run_tests

运行特定测试套件

./run_tests --gtest_filter="CalculatorTest.*"

运行类型化测试

./run_tests --gtest_filter=TypedTest"

运行参数化测试

./run_tests --gtest_filter=Parameterized"

列出所有测试

./run_tests --gtest_list_tests

输出 XML 报告

./run_tests --gtest_output=xml:test_report.xml

6.3 预期输出示例

\] Running 15 tests from 4 test suites. \[----------\] Global test environment set-up. \[----------\] 5 tests from CalculatorTest/0, where TypeParam = int \[ RUN \] CalculatorTest/0.AddTest \[ OK \] CalculatorTest/0.AddTest (0 ms) \[ RUN \] CalculatorTest/0.SubtractTest \[ OK \] CalculatorTest/0.SubtractTest (0 ms) ... \[----------\] 4 tests from AdditionCases/ParameterizedCalcTest \[ RUN \] AdditionCases/ParameterizedCalcTest.AddParameterized/0 \[ OK \] AdditionCases/ParameterizedCalcTest.AddParameterized/0 (0 ms) ... \[\] 15 tests from 4 test suites ran. (2 ms total) \[ PASSED \] 15 tests. 七、关键要点总结 特性 说明 非虚模板接口 使用 TYPED_TEST_SUITE 进行类型化测试 测试夹具 模板类 CalculatorTest 继承 ::testing::Test 参数化测试 TestWithParam + INSTANTIATE_TEST_SUITE_P 断言类型 EXPECT(继续执行)vs ASSERT_(终止) 浮点比较 EXPECT_DOUBLE_EQ / EXPECT_NEAR 异常测试 EXPECT_THROW CMake 集成 推荐 FetchContent 方式 八、常见问题解决 问题1: 找不到 gtest 库 解决: 使用 FetchContent 或手动编译 /usr/src/gtest 问题2: 链接错误 undefined reference 解决: 确保链接 pthread: target_link_libraries(... pthread) 问题3: 死亡测试不可用 解决: 编译时添加 -DGTEST_HAS_DEATH_TEST=1 问题4: 模板测试不编译 解决: 确保测试代码中包含完整模板定义(头文件) 这个完整示例涵盖了 Ubuntu 下 gtest 的安装、CMake 集成、模板类非虚接口测试的所有关键场景。您可以直接复制使用!

相关推荐
江畔何人初2 小时前
kubernetes中configmap与secret的区别
linux·运维·云原生·容器·kubernetes
三无少女指南2 小时前
开发者环境配置:用 Ollama 实现本地大模型部署(附下载慢的解决方案
c语言·开发语言·数据库·ubuntu
夏乌_Wx2 小时前
mybash:简易 Shell 实现的设计思路与核心模块解析
linux·服务器·前端
程序员爱德华2 小时前
Linux中的 源 和 Channels
linux·channels·
2501_918126912 小时前
stm32核心板是什么属性?
linux·c语言·stm32·嵌入式硬件·个人开发
500佰2 小时前
Hive常见故障多案例FAQ宝典 --项目总结(宝典一)
大数据·linux·数据仓库·hive·hadoop·云计算·运维开发
henry1010102 小时前
Ansible自动化运维全攻略(AI生成)
linux·运维·python·ansible·devops
Lxinccode2 小时前
AI编程(3) / claude code[3] : 更新apiKey
java·数据库·ai编程·claude code
vortex52 小时前
APT软件包管理从入门到精通
linux·运维·服务器·kali