๐Ÿ™‡โ€โ™€๏ธInterlocked

๐Ÿช๊ฒฝํ•ฉ ์กฐ๊ฑด (Race Condition)

2๋ฒˆ ํ…Œ์ด๋ธ”์—์„œ ์ฝœ๋ผ ํ•˜๋‚˜๋ฅผ ์ฃผ๋ฌธํ•˜๊ณ  ์ฃผ๋ฌธํ˜„ํ™ฉ์— ์˜ฌ๋ผ์˜ด ์ง์› 3๋ช…์ด ๋™์‹œ์— ์ฃผ๋ฌธํ˜„ํ™ฉ์„ ๋ณด๊ณ  ์ฝœ๋ผ๋ฅด 2๋ฒˆ ํ…Œ์ด๋ธ”์— ์คŒ ๊ฒฐ๊ตญ 2๋ฒˆ ํ…Œ์ด๋ธ”์— ์ฝœ๋ผ๋ฅผ 3๊ฐœ ๋ฐ›์Œ

์ˆœ์„œ๋ฅผ ์ง€ํ‚ค์ง€ ์•Š๊ณ  ๋™์‹œ๋‹ค๋ฐœ์ ์œผ๋กœ ์ผ์„ ํ•ด์„œ ์ƒ๊ธด ๋ฌธ์ œ

  • ๊ฒฝํ•ฉ ์กฐ๊ฑด ์˜ˆ์‹œ
static int number = 0;

static void Thread_1()
{
    for (int i = 0; i < 100000; i++)
        number++;
}

static void Thread_2()
{
    for (int i = 0; i < 100000; i++)
        number--;
}

static void Main(string[] args)
{
    Task t1 = new Task(Thread_1);
    Task t2 = new Task(Thread_2);
    t1.Start();
    t2.Start();

    Task.WaitAll(t1, t2);

    Console.WriteLine(number);
}

100000์„ ๋”ํ•˜๋Š” ์“ฐ๋ ˆ๋“œ์™€ 100000์„ ๋นผ๋Š” ์“ฐ๋ ˆ๋“œ

  • 0์ด ์•„๋‹ˆ๋ผ ๋‹ค๋ฅธ ๊ฒฐ๊ณผ ๊ฐ’์ด ๋‚˜์˜ด
  • ์ด์œ ๋Š” number++, numberโ€“๊ฐ€ ์›์ž์ ์œผ๋กœ ์ฒ˜๋ฆฌ ๋˜๋Š”๊ฒƒ์ด ์•„๋‹ˆ๊ธฐ ๋•Œ๋ฌธ
number++; // ์–ด์…ˆ๋ธ”๋ฆฌ์–ธ์–ด๋กœ ๋ฐ‘๊ณผ ๊ฐ™์ด ์ฒ˜๋ฆฌ ๋จ

int temp = number;
temp += 1;
number = temp;

๐ŸชInterlocked

  • ์›์ž์ ์œผ๋กœ ์ฒ˜๋ฆฌํ•ด์ฃผ๋Š” ํ•จ์ˆ˜
  • Interlocked ๊ณ„์—ด์˜ ํ•จ์ˆ˜
  • ๊ฐ€์‹œ์„ฑ ๋ฌธ์ œ๊นŒ์ง€ ํ•ด๊ฒฐํ•จ - ๋ฉ”๋ชจ๋ฆฌ๋ฒ ๋ฆฌ์–ด๊ฐ€ ์ˆจ์–ด์žˆ์Œ
  • volatile์ด ํ•„์š”์—†์Œ
static int number = 0;

static void Thread_1()
{
    // atomic = ์›์ž์„ฑ
    
    for (int i = 0; i < 100000; i++)
        // All or Nothing
        Interlocked.Increment(ref number); // ref๋กœ ์ฐธ์กฐ๋ฅผ ํ•ด์„œ ์ง์ ‘ ๊ฐ’์„ ์˜ฌ๋ฆฐ๋‹ค
}

static void Thread_2()
{
    for (int i = 0; i < 100000; i++)
        Interlocked.Decrement(ref number);
}

static void Main(string[] args)
{
    Task t1 = new Task(Thread_1);
    Task t2 = new Task(Thread_2);
    t1.Start();
    t2.Start();

    Task.WaitAll(t1, t2);

    Console.WriteLine(number);
}

interlocked๊ณ„์—ด ํ•จ์ˆ˜๋กœ ํ•ด๊ฒฐ๊ฐ€๋Šฅ

  • ๋ฉ€ํ‹ฐ์“ฐ๋ ˆ๋“œ์˜ ํ•จ์ •
int pre = number;
Interlocked.Increment(ref number);
int next = number;

์–ธ๋œป๋ณด๋ฉด next๋Š” pre๋ณด๋‹ค 1ํด๊ฒƒ ๊ฐ™์ง€๋งŒ ์•Œ์ˆ˜์—†๋‹ค

์‹ฑ๊ธ€ ์“ฐ๋ ˆ๋“œ์—์„œ๋Š” ๊ฐ€๋Šฅํ•˜์ง€๋งŒ ๋ฉ€ํ‹ฐ์“ฐ๋ ˆ๋“œ์—์„œ๋Š” ๋ˆ„๊ตฐ๊ฐ€๊ฐ€ ๋ณด๊ณ  ๊ฐ’์ด ๋ฐ”๋€”์ˆ˜ ์žˆ๊ธฐ ๋•Œ๋ฌธ!!

int afterValue = Interlocked.Increment(ref number);๊ฐ’์„ ๋นผ์˜ฌ๋ ค๋ฉด ์ด๋ ‡๊ฒŒ ํ•ด์•ผ๋จ

ํƒœ๊ทธ:

์นดํ…Œ๊ณ ๋ฆฌ:

์—…๋ฐ์ดํŠธ: