2017-10-11 5 views
-1

요청 번호를 기록하는 코드를 작성합니다.golang 동기화/원자 패키지?

package main 

import (
    "log" 
    "net/http" 
    "runtime" 
    "sync/atomic" 
) 

var count int32 = 0 

func test(w http.ResponseWriter, r *http.Request) { 
    count = atomic.LoadInt32(&count) 
    atomic.AddInt32(&count, 1) 
    log.Println("count:", count) 
} 
func main() { 
    runtime.GOMAXPROCS(runtime.NumCPU() - 1) 
    http.HandleFunc("/", test) 
    http.ListenAndServe(":8080", nil) 
} 

나는 동시성의 조건을 고려 했으므로 나는 원자적인 pacakge를 사용한다. 내가 아파치 AB 도구

ab -c 400 -n 1000 http://localhost:8080/ 

결과가 정확한지를 통해 코드를 테스트 : 이 result 그러나, 누군가는 그가 자신의 컴퓨터에 1004 또는 다른 번호를 가지고했다, 나는 코드를 여러 번 테스트를하지만, 한 결과가 내 컴퓨터에서 정확합니다. 내 방식에 문제가 있습니까? 나는 새로운데, 미리 감사드립니다.

+2

당신은 잘못 패키지를 사용하는; 'count = ...'와 같이'count' 변수를 직접 할당하거나 접근해서는 안됩니다. –

+0

사용중인 실제 코드를 보여주십시오. 이 예제는 로그 라인이'count' 값에 직접 접근하고 결과를'count'에 다시 할당하기 때문에 atomic의 유효한 사용법이 아닙니다 – JimB

+1

항상 경주 탐지기와'vet'를 사용하십시오. (또한,'ab'는 서버를 테스트하는 가난한 도구입니다. http/1.0이고 keepalive를 사용하지 않습니다.) – JimB

답변

0

sync/atomic 패키지를 잘못 사용하고 있습니다. 원자 변수가있는 경우 ALL 읽기와 쓰기는 원자 함수를 사용하여 수행해야합니다. count 변수가 아닌 원자에서 기록하거나 읽을되지 않도록 여기에

는 코드가 고정되어 있습니다 :

package main 

import (
    "log" 
    "net/http" 
    "runtime" 
    "sync/atomic" 
) 

var count int32 

func test(w http.ResponseWriter, r *http.Request) { 
    currentCount := atomic.LoadInt32(&count) 
    atomic.AddInt32(&count, 1) 
    log.Println("count:", currentCount) 
} 
func main() { 
    runtime.GOMAXPROCS(runtime.NumCPU() - 1) 
    http.HandleFunc("/", test) 
    http.ListenAndServe(":8080", nil) 
} 
+0

고마워, 알았다. – salamander