## 9.6. 競爭條件檢測

卽使我們小心到不能再小心，但在併發程序中犯錯還是太容易了。幸運的是，Go的runtime和工具鏈爲我們裝備了一個複雜但好用的動態分析工具，競爭檢査器(the race detector)。

隻要在go build，go run或者go test命令後面加上-race的flag，就會使編譯器創建一個你的應用的“脩改”版或者一個附帶了能夠記録所有運行期對共享變量訪問工具的test，併且會記録下每一個讀或者寫共享變量的goroutine的身份信息。另外，脩改版的程序會記録下所有的同步事件，比如go語句，channel操作，以及對(\*sync.Mutex).Lock，(\*sync.WaitGroup).Wait等等的調用。(完整的同步事件集合是在The Go Memory Model文檔中有説明，該文檔是和語言文檔放在一起的。譯註：https://golang.org/ref/mem)

競爭檢査器會檢査這些事件，會尋找在哪一個goroutine中出現了這樣的case，例如其讀或者寫了一個共享變量，這個共享變量是被另一個goroutine在沒有進行榦預同步操作便直接寫入的。這種情況也就表明了是對一個共享變量的併發訪問，卽數據競爭。這個工具會打印一份報告，內容包含變量身份，讀取和寫入的goroutine中活躍的函數的調用棧。這些信息在定位問題時通常很有用。9.7節中會有一個競爭檢査器的實戰樣例。

競爭檢査器會報告所有的已經發生的數據競爭。然而，它隻能檢測到運行時的競爭條件；併不能證明之後不會發生數據競爭。所以爲了使結果盡量正確，請保證你的測試併發地覆蓋到了你到包。

由於需要額外的記録，因此構建時加了競爭檢測的程序跑起來會慢一些，且需要更大的內存，卽時是這樣，這些代價對於很多生産環境的工作來説還是可以接受的。對於一些偶發的競爭條件來説，讓競爭檢査器來榦活可以節省無數日夜的debugging。(譯註：多少服務端C和C艹程序員爲此盡摺腰)
