Notice
Recent Posts
Recent Comments
Link
«   2025/02   »
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
Archives
Today
Total
관리 메뉴

Code Habit

Go ) sync.RWMutex 본문

카테고리 없음

Go ) sync.RWMutex

코드베어 2020. 6. 11. 08:00

읽기, 쓰기 뮤텍스는 읽기 동작과 쓰기 동작을 나누어 잠금(락)을 걸 수 있다.

  • 읽기 락(Read Lock): 읽기 락끼리는 서로를 막지 않는다. 하지만, 읽기 시도 중에 값이 바뀌면 안 되므로 쓰기 락은 막는다.
  • 쓰기 락(Write Lock): 쓰기 시도 중에 다른 곳에서 이전 값을 읽으면 안 되고, 다른 곳에서 값을 바꾸면 안 되므로 읽기, 쓰기 락 모두 막는다.

 

sync 패키지에서 제공하는 읽기, 쓰기 뮤텍스 구조체와 함수는 다음과 같다.

  • sync.RWMutex
  • func(rw *RWMutex) Lock(), / func(rw* RWMutex) Unlock(); 쓰기 뮤텍스 잠금 / 잠금 해제
  • func(rw *RWMutex) RLock(), / func(rw *RWMutex) RUnlock(); 읽기 뮤텍스 잠금 / 잠금 해제

 

사용 예제이다.

package main
 
import {
    "fmt"
    "runtime"
    "sync"
    "time"
}
 
func main() {
    runtime.GOMAXPROCS(runtime.NumCPU()) // 모든 CPU 사용
    
    var data int = 0
    var rwMutex = new(sync.RWMutex) // 읽기, 쓰기 뮤텍스 생성
 
    go func() {
        for i := 0; i < 3; i++ {
           rwMutex.Lock()   // 쓰기 뮤텍스 잠금
            data += 1
            fmt.Println("write : ", data)
            time.Sleep(10*time.Millisecond)  // 10 밀리초 대기
           rwMutex.UnLock() // 쓰기 뮤텍스 잠금 해제
        }
    }()
    
    go func()) {
        for i:-= 0; i < 3; i++ {
           rwMutex.RLock()  // 읽기 뮤텍스 잠금
            fmt.Println("read 1 : ", data)
            time.Sleep(1*time.Second)    // 1초 대기
           rwMutex.RUnlock() // 읽기 뮤텍스 잠금 해제
        }
    }()
 
    go func() {
        for i:= 0; i < 3; i++ {
           rwMutex.RLock()   // 읽기 뮤텍스 잠금
            fmt.Println("read 2 : ", data)
            time.Sleep(2 * time.Second)    // 2초 대기
           rwMutex.RUnlock() // 읽기 뮤텍스 잠금 해제
        }
    }()
 
    time.Sleep(10*time.Second)        // 10초 동안 프로그램 실행
}

 

RLock, RUnlock, Lock, Unlock 함수는 반드시 짝을 맞춰야 하며 짝이 맞지 않으면 데드락이 발생하므로 주의하자 !

읽기, 쓰기 뮤텍스는 중요한 쓰기 작업을 할 때 다른 곳에서 이전 데이터를 읽지 못하도록 방지하거나, 읽기 작업을 할 때 데이터가 바뀌는 상황을 방지할 때 사용한다. 특히 읽기, 쓰기 뮤텍스는 쓰기 동작보다 읽기 동작이 많을 때 유리하다.