Go test工具
Go語言中測試依賴go test命令。
go test命令是一個按照一定約定和組織的測試代碼的驅動程序。在包目錄內,所有以_test.go為后綴名的源代碼文件都是go test 測試的一部分,不會被go build編譯到最終的可執行文件中。
測試函數類型
在*_test.go文件中有三種類型的函數:單元測試函數,基准測試函數和示例函數。
| 類型 | 格式 | 作用 |
| 測試函數 | 函數名綴為Test | 測試程序的一些邏輯行為是否正確 |
| 基准函數 | 函數名前綴為Benchmark | 測試函數的內存占用和運行效率的性能數據 |
| 示例函數 | 函數名前綴為Example | 為文檔提高示例文檔 |
測試規則
測試規則主要為文件命名與放置規則:
- 測試源文件名應是_test結尾的go文件,例如:add_test.go;
- 測試代碼和業務代碼是分開的,但兩者應該位於同一包下;
- 測試源文件所在的包應該位於$GOPATH/src目錄下;
- 測試文件必須導入"testing"包;
測試函數
每個測試函數必須導入testing包,測試函數的基本格式如下:
func TestName(t *testing.T){
//...
}
測試函數的名字必須以Test開頭,可選的后綴名必須以大寫字母開頭,舉幾個例子:
func TestAdd(t *testing.T){...}
func TestSum(t *testing.T){...}
func TestLog(t *testing.T){...}
其中參數t用於報告測試失敗和附加的日志信息。testing.T擁有的方法如下:
func (c *T)Error(args ...interface{})
func (c *T)Errorf(format string,args ...interface{})
func (c *T)Fail()
func (c *T)Failnow()
func (c *T)Failed()bool
func (c *T)Fatal(args ...interface{})
func (c *T)Fatal(format string ,args ...interface{})
func (c *T)Log()(args ...interface{})
func (c *T)Logf(format string ,args ...interface{})
func (c *T)Name() string
func (c *T)Paralled()
func (c *T)Run(name string,f func(t *T)) bool
func (c *T)Skip(args ...interface{})
func (c *T)SkipNow()
func (c *T)Skipf(format string ,args ...interface{})
func (c *T)Skipped() bool
go test參數
-bench [正則表達式]:僅運行與正則表達式匹配的基准,默認情況下,不運行基准測試。如果要運行所有的基准測試函數,使用-bench .或者-bench=.。
-benchtime [時間]:表示運行多長時間的基准測試,默認值為1秒。例如:-benchtime 1h30s。
-count n:運行每個測試和基准多少次,默認為1,如果設置了-cpu,則為每個GOMAXPROCS運行n次,例子函數總是運行一次。
-cover:啟用覆蓋率分析,由於覆蓋率通過在編譯之前注釋源代碼來工作,因此啟用覆蓋率的編譯和測試失敗,可能會出現報告與原始文件行號不對應的情況。
-covermode set,count,atomic:為正在測試的包設置覆蓋率分析模式,除非啟用-race,否則默認為set,在這種情況下它是原子的。
set,布爾值,表示這句聲明是否有效
count,int類型,這句聲明運行多少次
atomic,int類型,在多線程測試中使用,原子操作。
-coverpkg pattern1,pattern2,pattern3:將每個測試中的覆蓋率分析應用於模式匹配的包,默認情況下,每個測試僅分析正在測試的包。
-cpu 1,2,4:指定應為其執行測試或基准測試的GOMAXPROCS的值的列表,默認值是GOMAXPROCS的當前值。
-failfast:表示在第一次測試失敗后不要開始新的測試。
-list [正則表達式]:只是列出與正則表達式匹配的測試、基准測試或例子,不會運行任何測試。
-parallel n:表示運行的最大測試數,默認情況下,它設置為GOMAXPROCS的值。
-run [正則表達式]:僅僅運行與正則表達式匹配的那些測試和例子,匹配時可能父項也會運行,例如:-run = X/Y,匹配運行所有與X匹配的測試的結果,即使沒有匹配到子測試。
-timeout [時間]:如果測試文件運行的時間超過設置的時間,就會出現panic。如果設置的時間為0,則表示timeout不可用。默認是10分鍾。
-v:會打印詳細的測試結果,即使是在測試成功的情況。
單元測試
1.在src目錄下創建mytest目錄,創建兩個文件Add.go和Add_test.go文件;
Add.go:
package main
func addNum(n int) (result int) {
for i := 0; i <= n; i++ {
result = result + i
}
return
}
Add_test.go:
package main
import (
"testing"
)
//單元測試函數
func TestAddNum(t *testing.T) {
if addNum(100) != 5050 {
t.Fatal("addNum error!")
}
}
2.進入src目錄下的mytest目錄下,執行go test命令
3.返回結果
PASS ok mytest 0.056s
加入基准測試
1.修改Add_test.go:
package main
import (
"testing"
)
//單元測試函數
func TestAddNum(t *testing.T) {
if addNum(100) != 5050 {
t.Fatal("addNum error!")
}
}
//基准測試函數
func BenchmarkAddNum(b *testing.B) {
for i := 0; i < b.N; i++ {
if addNum(100) != 5050 {
b.Fatal("addNum")
}
}
}
2.執行go test -bench=.
3.返回結果
goos: windows goarch: amd64 pkg: MyDemo/mytest BenchmarkAddNum-4 20000000 74.3 ns/op PASS ok mytest 1.615s
顯示執行addNum函數花費的平均時間是1.615s,執行了20000000次,每74.3ns的速度運行一次循環。
特殊功能
指定基准測試函數:通過-bench可以指定只測試哪個基准函數,如果沒有指定,則測試所有基准函數。
go test -bench=. 測試所有基准函數
go test -bench=Alloc 指定只測試Benchmark_Alloc() 基准函數
自定義測試時間:通過-benchtime參數可以自定義測試時間。(基准測試原理:基准測試框架對一個測試用例的默認測試時間是 1 秒。開始測試時,當以 Benchmark 開頭的基准測試用例函數返回時還不到 1 秒,那么 testing.B 中的 N 值將按 1、2、5、10、20、50……遞增,同時以遞增后的值重新調用基准測試用例函數。)
go test -v -bench=. -benchtime=5s
測試內存:基准測試可以對一段代碼可能存在的內存分配進行統計:通過-benchmem參數以顯示內存分配情況。
go test -bench=. -benchmem
返回信息字段:
Benchmarkxxx-4 格式為基准測試函數名-GOMAXPROCS,后面的-4代表測試函數運行時對應的CPU核數 1 表示執行的次數 xx ns/op 表示每次的執行時間 xx B/op 表示每次執行分配的總字節數(內存消耗) xx allocs/op 表示每次執行發生了多少次內存分配
