Arthur's Blog

λ™μ‹œμ„± 문제λ₯Ό μ œμ–΄ν•˜λŠ” 방법 λ³Έλ¬Έ

Language/Java

λ™μ‹œμ„± 문제λ₯Ό μ œμ–΄ν•˜λŠ” 방법

Leeseojune53 2023. 6. 28. 22:43

πŸ“Œ μ •μ˜

λ©€ν‹° μŠ€λ ˆλ“œ ν™˜κ²½μ—μ„œ μ—¬λŸ¬ μŠ€λ ˆλ“œκ°€ λ™μ‹œμ— ν•˜λ‚˜μ˜ μžμ›μ„ κ³΅μœ ν•  λ•Œ λ™μ‹œμ„± 문제, λ°λ“œλ½ λ“± μ—¬λŸ¬ λ¬Έμ œκ°€ λ°œμƒν•œλ‹€. ν•΄λ‹Ή 문제 쀑 λ™μ‹œμ„± 문제λ₯Ό μ œμ–΄ν•˜λŠ” 방법을 μ•Œμ•„λ³΄μž.

1️⃣ μ•”μ‹œμ  잠금

ν•˜λ‚˜μ˜ μŠ€λ ˆλ“œκ°€ ν•΄λ‹Ή λ©”μ†Œλ“œλ₯Ό μ‹€ν–‰ν•˜κ³  μžˆμ„ λ•Œ λ‹€λ₯Έ μŠ€λ ˆλ“œκ°€ ν•΄λ‹Ή λ©”μ†Œλ“œλ₯Ό μ‹€ν–‰ν•˜μ§€ λͺ»ν•˜κ³  λŒ€κΈ°ν•˜κ²Œ ν•˜λŠ” 방법. μž κΈˆμ€ λ©”μ†Œλ“œ, λ³€μˆ˜μ— 각 각 κ±Έ 수 μžˆλ‹€.

😎 예제

class Count {
    private int count;
    
    public synchronized int view() {
        return count++;
    }
}
 

μœ„μ˜ μ˜ˆμ œλŠ” λ©”μ†Œλ“œ μž κΈˆμ΄λ‹€.

 
class Count {
    private Integer count;
    public int view() {
        synchronized (this.count) {
            return count++;
        }
    }
}​

2️⃣ λͺ…μ‹œμ  잠금

synchronized ν‚€μ›Œλ“œ 없이 λͺ…μ‹œμ μœΌλ‘œ ReentrantLock을 μ‚¬μš©ν•˜λŠ” 잠금.

μš΄μ˜μ²΄μ œμ—μ„œ μž„κ³„μ˜μ—­κ³Ό λΉ„μŠ·ν•œ λŠλ‚Œμ΄λ‹€.

😎 μ˜ˆμ‹œ

public class CountingTest {
    public static void main(string[] args) {
        Count count = new Count();
        for (int i = 0; i < 100; i++) {
            new Thread() {
                public void run() {
                    for(int j = 0; j < 1000; j++) {
                        count.getLock().lock();
                        System.out.println(count.view());
                        count.getLock().unlock();
                    }
                }
            }.start();
        }
    }
}

class Count {
    private int count = 0;
    private Lock lock = new ReentrantLock();
    public int view() {
        return count++;
    }
    public Lock getLock() {
        return lock;
    }
}
 

3️⃣ volatile

μŠ€λ ˆλ“œλ“€μ΄ μžμ›μ— read, writeλ₯Ό 진행할 λ•Œ 항상 λ©”λͺ¨λ¦¬μ— μ ‘κ·Όν•˜μ§€ μ•ŠλŠ”λ‹€. μ„±λŠ₯의 ν–₯상을 μœ„ν•΄ CPU μΊμŠ€μ— 값을 μ €μž₯ν•˜κΈ° λ•Œλ¬Έμ— ν•΄λ‹Ή 값이 λ©”λͺ¨λ¦¬μ— μ €μž₯된 μ‹€μ œ κ°’κ³  항상 μΌμΉ˜ν•˜λŠ”μ§€ 보μž₯ν•  수 μ—†λ‹€.

메인 λ©”λͺ¨λ¦¬μ— μ €μž₯된 μ‹€μ œ μžμ›μ˜ 값을 λ³Ό 수 μžˆλŠ” κ°œλ…μ„ μžμ›μ˜ κ°€μ‹œμ„±μ΄λΌκ³  λΆ€λ₯Έλ‹€.

volatile은 μœ„μ™€ 같은 CPU μΊμ‹œ μ‚¬μš©μ„ λ§‰λŠ”λ‹€. λ³€μˆ˜μ— volatile ν‚€μ›Œλ“œλ₯Ό λΆ™μ—¬μ£Όλ©΄ ν•΄λ‹Ή λ³€μˆ˜λŠ” μΊμ‹œμ— μ €μž₯λ˜λŠ” λŒ€μƒμ—μ„œ μ œμ™Έλœλ‹€. μΊμ‹œ μ‚¬μš©μœΌλ‘œ μΈν•œ ν…Œμ΄ν„° 뢈일치λ₯Ό λ§‰λŠ”λ‹€.

4️⃣ Concurrent

Atomic~~와 같은 ν΄λž˜μŠ€λŠ” λ‹¨μˆœν•œ 증감연산을 λ©”μ†Œλ“œλ‘œ μ œκ³΅ν•΄μ€€λ‹€. ν•΄λ‹Ή 클래슀의 λ©”μ†Œλ“œλŠ” λ‚΄λΆ€μ μœΌλ‘œ Thread-safeν•˜κ²Œ κ΅¬μ‘°ν™”λ˜μ–΄ μžˆλ‹€.

Concurrent~~와 같은 μ»¬λž™μ…˜λ“€μ€ 락을 μ‚¬μš©ν•  λ•Œ λ°œμƒν•˜λŠ” μ„±λŠ₯ μ €ν•˜λ₯Ό μ΅œμ†Œν•œμœΌλ‘œ λ§Œλ“€μ–΄λ‘μ—ˆλ‹€.