GTest学习笔记(六)

参考博客:

Advanced googletest Topics | GoogleTest

玩转Google开源C++单元测试框架Google Test系列(gtest)之三 - 事件机制 - CoderZh - 博客园 (cnblogs.com)

前言:

本文主要是在cpp文件里使用了官网提供的示例代码来熟悉GTest的三种事件机制(TestCase级别、TestSuite级别、全局),为了方便简洁,源码中没有定义对应的头文件,只有cpp文件。

1 TestCase级别

1.1使用方法
  • 编写一个类FooTest,继承testing::Test
  • 在FooTest里实现SetUp()和TearDown()方法,SetUp方法会在每个TestCase执行开始前执行;TearDown方法会在每个TestCase执行完成后执行
  • 编写TestCase时,要将第一个参数TestFixtureName(TEST_F函数)/TestSuiteName(TEST函数)要写成FooTest

2 TestSuite级别

出现的原因: GTest为每一个test创建一个fixture对象,来让每一个test独立并且易于调试。但是,有时候test使用的资源设置起来代价很高,这使得每个test创建一个fixture对象的模型代价非常高。

适用场景: 如果test并不会去改变资源,那么多个test共享一份资源也就没有什么问题。

2.1 使用方法
  • 在测试固件类中,将一些成员变量声明为静态的,这样就可以保留共享的资源
  • 在测试固件类外,定义那些静态成员变量, 可选地给它们初始值。
  • 在同一个测试固件类中:定义一个 static void SetUpTestSuite()函数,用来配置共享的资源; 定义一个static void TearDownTestSuite()函数用来释放这些资源。在运行这个测试固件类中的第一个测试用例之前,GTest会自动调用SetUpTestSuite() ,在运行完测试固件类中最后一个测试用例之后,GTest会自动调用TearDownTestSuite()

3 Program级别

3.1使用方法
  • 编写一个类Environment,继承testing::Environment
  • 在Environment里重写SetUp()TearDown()方法,SetUp方法会在所有的TestCase执行开始前执行;TearDown方法会在所有TestCase执行完成后执行
  • 实例化一个Environment对象,并调用AddGlobalTestEnvironment(Environment* env)方法;注意AddGlobalTestEnvironment(Environment* env)的调用要在RUN_ALL_TESTS()

3.2 注意事项

  • 允许注册多个环境对象(我理解的是允许声明多个类继承testing::Environment,然后注册不同类的多个环境对象吧,同一个环境类声明多个对象没什么意义吧?)。 在这个套件中,它们的SetUp()将按注册的顺序调用,而TearDown()将按相反的顺序调用
  • googletest拥有注册的环境对象的所有权。因此,请不要自行删除

4 运行实例

源代码

该项目由test.pp、testAddIntegers.cpp、testSubIntegers.cpp构成

test.cpp:

#include <gtest/gtest.h>


class Environment : public ::testing::Environment {
public:
    ~Environment() override {}

    // Override this to define how to set up the environment.
    void SetUp() override {
        printf("Environment类:全局级别SetUp函数执行!\n");
    }

    // Override this to define how to tear down the environment.
    void TearDown() override {
        printf("Environment类:全局级别TearDown函数执行!\n");
    }
};
class EnvironmentNew : public ::testing::Environment {
public:
    ~EnvironmentNew() override {}

    // Override this to define how to set up the environment.
    void SetUp() override {
        printf("EnvironmentNew类:全局级别SetUp函数执行!\n");
    }

    // Override this to define how to tear down the environment.
    void TearDown() override {
        printf("EnvironmentNew类:全局级别TearDown函数执行!\n");
    }
};


int main(int argc, char** argv) {
    ::testing::InitGoogleTest(&argc, argv);
    // 定义了两个环境对象,以达到添加两种全局事件的目的
    Environment* global;
    global = new Environment();
    //注意要定义指针对象,不能定义类对象然后参数取地址(这样做只定义一个类对象不影响运行,但是定义两个环境对象时运行结果会报堆栈的错误)
    AddGlobalTestEnvironment(global);      
    EnvironmentNew* globalNew;
    globalNew = new EnvironmentNew();
    AddGlobalTestEnvironment(globalNew);
    return RUN_ALL_TESTS();
}

testAddIntegers.cpp:

#include "stdio.h"
#include "gtest/gtest.h"


namespace myAdd {
    namespace projectAdd {
        namespace {
            int add(int a, int b)
            {
                return a + b;
            }

            // The fixture for testing class Foo.
            class AddIntegers : public ::testing::Test {
            protected:
                // You can remove any or all of the following functions if their bodies would
                // be empty.

                static void SetUpTestSuite() {
                    // Avoid reallocating static objects if called in subclasses of FooTest.
                    printf("AddIntegers类TestSuite级别SetUp函数执行!\n");
                }

                // Per-test-suite tear-down.
                // Called after the last test in this test suite.
                // Can be omitted if not needed.
                static void TearDownTestSuite() {
                    printf("AddIntegers类TestSuite级别TearDown函数执行!\n");

                }



                AddIntegers() {
                    // You can do set-up work for each test here.
                    printf("AddIntegers类构造函数执行!\n");
                }

                ~AddIntegers() override {
                    // You can do clean-up work that doesn't throw exceptions here.
                    printf("AddIntegers类析构函数执行!\n");
                }

                // If the constructor and destructor are not enough for setting up
                // and cleaning up each test, you can define the following methods:

                void SetUp() override {
                    // Code here will be called immediately after the constructor (right
                    // before each test).
                    printf("AddIntegers类TestCase级别SetUp函数执行!\n");
                }

                void TearDown() override {
                    // Code here will be called immediately after each test (right
                    // before the destructor).
                    printf("AddIntegers类TestCase级别TearDown函数执行!\n");
                }

                // Class members declared here can be used by all tests in the test suite
                // for Foo.
            };

            // Tests that the Foo::Bar() method does Abc.
            TEST_F(AddIntegers, TestAdd1) {
                EXPECT_EQ(add(2, 3), 5);
            }

            // Tests that Foo does Xyz.
            TEST_F(AddIntegers, TestAdd2) {
                EXPECT_EQ(add(2, 1), 7);
            }

        }  // namespace
    }  // namespace project
}  // namespace my

testSubIntegers.cpp:

#include "stdio.h"
#include "gtest/gtest.h"


namespace mySub {
    namespace projectSub {
        namespace {
            int sub(int a, int b)
            {
                return a - b;
            }

            // The fixture for testing class Foo.
            class SubIntegers : public ::testing::Test {
            protected:
                // You can remove any or all of the following functions if their bodies would
                // be empty.

                static void SetUpTestSuite() {
                    // Avoid reallocating static objects if called in subclasses of FooTest.
                    printf("SubIntegers类TestSuite级别SetUp函数执行!\n");
                }

                // Per-test-suite tear-down.
                // Called after the last test in this test suite.
                // Can be omitted if not needed.
                static void TearDownTestSuite() {
                    printf("SubIntegers类TestSuite级别TearDown函数执行!\n");

                }



                SubIntegers() {
                    // You can do set-up work for each test here.
                    printf("SubIntegers类构造函数执行!\n");
                }

                ~SubIntegers() override {
                    // You can do clean-up work that doesn't throw exceptions here.
                    printf("SubIntegers类析构函数执行!\n");
                }

                // If the constructor and destructor are not enough for setting up
                // and cleaning up each test, you can define the following methods:

                void SetUp() override {
                    // Code here will be called immediately after the constructor (right
                    // before each test).
                    printf("SubIntegers类TestCase级别SetUp函数执行!\n");
                }

                void TearDown() override {
                    // Code here will be called immediately after each test (right
                    // before the destructor).
                    printf("SubIntegers类TestCase级别TearDown函数执行!\n");
                }

                // Class members declared here can be used by all tests in the test suite
                // for Foo.
            };

            // Tests that the Foo::Bar() method does Abc.
            TEST_F(SubIntegers, TestSub1) {
                EXPECT_EQ(sub(9, 3), 6);
            }

            // Tests that Foo does Xyz.
            TEST_F(SubIntegers, TestSub2) {
                EXPECT_EQ(sub(2, 2), 0);
            }

        }  // namespace
    }  // namespace project
}  // namespace my

运行结果:

在这里插入图片描述

内容如有错误,敬请指正!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值