[C# 서버] Thread Local Storage

Yerin·2023년 9월 20일

C# 게임 서버

목록 보기
11/13

무조건 멀티 쓰레드 환경이라고 해서 Lock만 걸고 들어가는 것이 최선의 방법은 아닐 수 있다.

유저들이 한 쪽 구역에 몰리면 어떻게 되겠는가?

TLS를 이용하자!

ThreadLocal

전역변수는 전역변수인데 쓰레드마다 고유의 공간이 생겼다.

using System;
using System.ComponentModel;
using System.Threading;

namespace SeverCore
{  
    class Program
    {
        static ThreadLocal<string> ThreadName = new ThreadLocal<string>();

        static void WhoAmI()
        {
            ThreadName.Value = $"My Name Is {Thread.CurrentThread.ManagedThreadId}";

            Thread.Sleep(1000);

            Console.WriteLine( ThreadName.Value);
        }
        static void Main(string[] args)
        {
            Parallel.Invoke(WhoAmI, WhoAmI, WhoAmI, WhoAmI, WhoAmI, WhoAmI, WhoAmI);
        }
    }
}

하지만 위 경우는 새로 실행될 때마다 덮어씌어지는 경우가 생긴다.

따라서 ThreadName이라는 Value가 세팅이 안 되었을 경우에만 실행되도록 한다.

using System;
using System.ComponentModel;
using System.Threading;

namespace SeverCore
{  
    class Program
    {
        static ThreadLocal<string> ThreadName = new ThreadLocal<string>(() => { return $"My Name Is {Thread.CurrentThread.ManagedThreadId}"; });

        static void WhoAmI()
        {
            bool repeat = ThreadName.IsValueCreated;
            if(repeat)
                Console.WriteLine( ThreadName.Value + " (repeat)");
            else
                Console.WriteLine(ThreadName.Value );
        }
        static void Main(string[] args)
        {
            ThreadPool.SetMinThreads(1, 1);
            ThreadPool.SetMaxThreads(3, 3);
            Parallel.Invoke(WhoAmI, WhoAmI, WhoAmI, WhoAmI, WhoAmI, WhoAmI, WhoAmI);
            
            ThreadName.Dispose();
        }
    }
}

Lock을 한 번 걸고 최대한 많은 일감을 빼올 수 있다.
즉 부화가 줄어든다.

profile
재밌는 코딩 공부

0개의 댓글