摘自:https://www.cnblogs.com/helloworldcode/p/9606838.html
安裝GTest
1、安裝源代碼
下載gtest,release-1.8.0
git clone https://github.com/google/googletest
gtest編譯
cd googletest
生成Makefile文件(先安裝cmake,brew install cmake),繼續輸入命令編譯:
cmake CMakeLists.txt
執行make,生成兩個靜態庫:libgtest.a libgtest_main.a
make
拷貝到系統目錄,注意,如果下訴目錄位置在不同版本位置有變動,用find . -name "libgtest*.a" 找到位置
sudo cp libgtest*.a /usr/lib
sudo cp –a include/gtest /usr/include
檢查是否安裝成功
可以寫一個簡單的測試代碼如下:
1
2
3
4
5
6
7
8
9
10
11
|
#include<gtest/gtest.h>
int
add(
int
a,
int
b){
return
a+b;
}
TEST(testCase,test0){
EXPECT_EQ(add(2,3),5);
}
int
main(
int
argc,
char
**argv){
testing::InitGoogleTest(&argc,argv);
return
RUN_ALL_TESTS();
}
|
在該文件的終端輸入編譯指令:
gqx@gqx-Lenovo-Product:~/workplace/aaaa$ g++ test.cc -lgtest -lpthread
gqx@gqx-Lenovo-Product:~/workplace/aaaa$ ./a.out
即得到如下顯示結果:
GTest的一些基本概念
要測試一個類或函數,我們需要對其行為做出斷言。當一個斷言失敗時,Google Test會在屏幕上輸出該代碼所在的源文件及其所在的位置行號,以及錯誤信息。也可以在編寫斷言時,提供一個自定義的錯誤信息,這個信息在失敗時會被附加在Google Test的錯誤信息之后。
斷言常常成對出現,它們都測試同一個類或者函數,但對當前功能有着不同的效果。ASSERT_*版本的斷言失敗時會產生致命失敗,並結束當前函數。EXPECT_*版本的斷言產生非致命失敗,而不會中止當前函數。通常更推薦使用EXPECT_*斷言,因為它們運行一個測試中可以有不止一個的錯誤被報告出來。但如果在編寫斷言如果失敗,就沒有必要繼續往下執行的測試時,你應該使用ASSERT_*斷言。 因為失敗的ASSERT_*斷言會立刻從當前的函數返回,可能會跳過其后的一些的清潔代碼,這樣也許會導致空間泄漏。
GTest的斷言
1、布爾值檢查
Fatal assertion |
Nonfatal assertion |
Verifies |
ASSERT_TRUE(condition); |
EXPECT_TRUE(condition); |
condition is true |
ASSERT_FALSE(condition); |
EXPECT_FALSE(condition); |
condition is false |
2、數值型數據檢查
Fatal assertion |
Nonfatal assertion |
Verifies |
ASSERT_EQ(expected, actual); |
EXPECT_EQ(expected, actual); |
expected == actual |
ASSERT_NE(val1, val2); |
EXPECT_NE(val1, val2); |
val1 != val2 |
ASSERT_LT(val1, val2); |
EXPECT_LT(val1, val2); |
val1 < val2 |
ASSERT_LE(val1, val2); |
EXPECT_LE(val1, val2); |
val1 <= val2 |
ASSERT_GT(val1, val2); |
EXPECT_GT(val1, val2); |
val1 > val2 |
ASSERT_GE(val1, val2); |
EXPECT_GE(val1, val2); |
val1 >= val2 |
3、字符串比較
Fatal assertion |
Nonfatal assertion |
Verifies |
ASSERT_STREQ(expected_str, actual_str); |
EXPECT_STREQ(expected_str, actual_str); |
兩個C字符串有相同的內容 |
ASSERT_STRNE(str1, str2); |
EXPECT_STRNE(str1, str2); |
兩個C字符串有不同的內容 |
ASSERT_STRCASEEQ(expected_str, actual_str); |
EXPECT_STRCASEEQ(expected_str, actual_str); |
兩個C字符串有相同的內容,忽略大小寫 |
ASSERT_STRCASENE(str1, str2); |
EXPECT_STRCASENE(str1, str2); |
兩個C字符串有不同的內容,忽略大小寫 |
4、異常檢查
Fatal assertion |
Nonfatal assertion |
Verifies |
ASSERT_THROW(statement, exception_type); |
EXPECT_THROW(statement, exception_type); |
statement throws an exception of the given type |
ASSERT_ANY_THROW(statement); |
EXPECT_ANY_THROW(statement); |
statement throws an exception of any type |
ASSERT_NO_THROW(statement); |
EXPECT_NO_THROW(statement); |
statement doesn't throw any exception |
5、浮點型檢查
Fatal assertion |
Nonfatal assertion |
Verifies |
ASSERT_FLOAT_EQ(expected, actual); |
EXPECT_FLOAT_EQ(expected, actual); |
the two float values are almost equal |
ASSERT_DOUBLE_EQ(expected, actual); |
EXPECT_DOUBLE_EQ(expected, actual); |
the two double values are almost equal |
對相近的兩個數比較:
Fatal assertion |
Nonfatal assertion |
Verifies |
ASSERT_NEAR(val1, val2, abs_error); |
EXPECT_NEAR(val1, val2, abs_error); |
the difference between val1 and val2 doesn't exceed the given absolute error |
6、此外還有類型檢查、謂詞檢查等
事件機制
全局事件
要實現全局事件,必須寫一個類,繼承testing::Environment類,實現里面的SetUp和TearDown方法。
1. SetUp()方法在所有案例執行前執行
2. TearDown()方法在所有案例執行后執行
還需要告訴gtest添加這個全局事件,我們需要在main函數中通過testing::AddGlobalTestEnvironment方法將事件掛進來,也就是說,我們可以寫很多個這樣的類,然后將他們的事件都掛上去。
TestSuite事件
我們需要寫一個類,繼承testing::Test,然后實現兩個靜態方法
1. SetUpTestCase() 方法在第一個TestCase之前執行
2. TearDownTestCase() 方法在最后一個TestCase之后執行
在編寫測試案例時,我們需要使用TEST_F這個宏,第一個參數必須是我們上面類的名字,代表一個TestSuite。
TestCase事件
TestCase事件是掛在每個案例執行前后的,實現方式和上面的幾乎一樣,不過需要實現的是SetUp方法和TearDown方法:
1. SetUp()方法在每個TestCase之前執行
2. TearDown()方法在每個TestCase之后執行
以下案例解決說明上述三個事件的使用
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
|
#include<gtest/gtest.h>
#include<map>
#include<iostream>
using
namespace
std;
class
Student{
public
:
Student(){
age=0;
}
Student(
int
a){
age=a;
}
void
print(){
cout<<
"*********** "
<<age<<
" **********"
<<endl;;
}
private
:
int
age;
};
class
FooEnvironment :
public
testing::Environment{
public
:
virtual
void
SetUp()
{
std::cout <<
"Foo FooEnvironment SetUP"
<< std::endl;
}
virtual
void
TearDown()
{
std::cout <<
"Foo FooEnvironment TearDown"
<< std::endl;
}
};
static
Student *s;
//在第一個test之前,最后一個test之后調用SetUpTestCase()和TearDownTestCase()
class
TestMap:
public
testing::Test
{
public
:
static
void
SetUpTestCase()
{
cout<<
"SetUpTestCase()"
<<endl;
s=
new
Student(23);
}
static
void
TearDownTestCase()
{
delete s;
cout<<
"TearDownTestCase()"
<<endl;
}
void
SetUp()
{
cout<<
"SetUp() is running"
<<endl;
}
void
TearDown()
{
cout<<
"TearDown()"
<<endl;
}
};
TEST_F(TestMap, Test1)
{
// you can refer to s here
s->print();
}
int
main(
int
argc,
char
** argv)
{
testing::AddGlobalTestEnvironment(
new
FooEnvironment);
testing::InitGoogleTest(&argc, argv);
return
RUN_ALL_TESTS();
}
|
相關結果和說明如下:
參數化
當考慮多次要為被測函數傳入不同的值的情況時,可以按下面的方式去測試。必須添加一個類,繼承testing::TestWithParam<T>。其中T就是你需要參數化的參數類型,如下面的案例是int型參數。(官方文檔上的案例)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
|
#include<gtest/gtest.h>
// Returns true iff n is a prime number.
bool
IsPrime(
int
n)
{
// Trivial case 1: small numbers
if
(n <= 1)
return
false
;
// Trivial case 2: even numbers
if
(n % 2 == 0)
return
n == 2;
// Now, we have that n is odd and n >= 3.
// Try to divide n by every odd number i, starting from 3
for
(
int
i = 3; ; i += 2) {
// We only have to try i up to the squre root of n
if
(i > n/i)
break
;
// Now, we have i <= n/i < n.
// If n is divisible by i, n is not prime.
if
(n % i == 0)
return
false
;
}
// n has no integer factor in the range (1, n), and thus is prime.
return
true
;
}
class
IsPrimeParamTest :
public
::testing::TestWithParam<
int
>{};
TEST_P(IsPrimeParamTest, HandleTrueReturn)
{
int
n = GetParam();
EXPECT_TRUE(IsPrime(n));
}
//被測函數須傳入多個相關的值
INSTANTIATE_TEST_CASE_P(TrueReturn, IsPrimeParamTest, testing::Values(3, 5, 11, 23, 17));
int
main(
int
argc,
char
**argv)
{
testing::InitGoogleTest(&argc, argv);
return
RUN_ALL_TESTS();
}
|
注:部分內容摘自網絡(http://www.cnblogs.com/coderzh/archive/2009/04/06/1426755.html)