본문 바로가기

C# 문법

[C#] C# 5.0 await / async - 비동기 FileRead => ReadAsync

await / async

  • C# 5.0에서는 await / async 예약어가 추가되었습니다.
  • 이 예약어를 이용하면 비동기 호출을 사용할 수 있습니다.

만약 동기 FileRead 상태라면

    public void Run()
    {
        //데이터 Read를 동기로 호출!
        SyncRead();
        //호출이 완료되고 Main에서는 1ms로 숫자를 표시
        for(int i=0; i< 30; i++)
        {
            Console.WriteLine(i);
            Thread.Sleep(1);
        }
    }
    private async void SyncRead()
    {
        using (FileStream fs = new FileStream(@"./YangbengHis.xml", FileMode.Open, FileAccess.Read))
        {
            byte[] buffer = new byte[fs.Length];
            //호출하기 전에 Thread ID와
            Console.WriteLine($"Before ReadSync : {Thread.CurrentThread.ManagedThreadId}");
            fs.Read(buffer, 0, buffer.Length);
            //호출 후 Thread의 ID 비교
            Console.WriteLine($"Before ReadSync : {Thread.CurrentThread.ManagedThreadId}");
            string txt = Encoding.UTF8.GetString(buffer);
            Console.WriteLine(txt);
        }
    }

결과

Before ReadSync : 1
Before ReadSync : 1
<?xml version="1.0" encoding="utf-8"?>
<History xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <Name>Yangbeng</Name>
  <Age>33</Age>
  <Friends>
    <string>범범조조</string>
    <string>쏭</string>
    <string>태발</string>
    <string>털</string>
    <string>쩌주</string>
  </Friends>
</History>
0
1
2
3
4...
  • 위 코드와 같이 동기로 FileRead를 진행하게 되면, 파일을 모두 읽을 때 까지 기다린 후 시간을 표시하게 됩니다.

비동기 FileRead라면

    public void Run()
    {
        //데이터 Read를 비동기로 호출!
        AwaitRead();
        //호출 되고 있는동안 Main에서는 1ms로 숫자를 표시
        for (int i = 0; i < 30; i++)
        {
            Console.WriteLine(i);
            Thread.Sleep(1);
        }
    }
    private async void AwaitRead()
    {
        using (FileStream fs = new FileStream(@"./YangbengHis.xml", FileMode.Open, FileAccess.Read))
        {
            byte[] buffer = new byte[fs.Length];
            //awit 호출하기 전에 Thread ID와
            Console.WriteLine($"Before ReadAsync : {Thread.CurrentThread.ManagedThreadId}");

            await fs.ReadAsync(buffer, 0, buffer.Length);
            //awit 호출 후 Thread의 ID 가 다르다.!!!
            Console.WriteLine($"Before ReadAsync : {Thread.CurrentThread.ManagedThreadId}");
            //아래의 두 줄의 내용은 readAsysnc가 끝난 이후 비동기 호출이 된다.
            string txt = Encoding.UTF8.GetString(buffer);
            Console.WriteLine(txt);
        }
    }

결과

Before ReadAsync : 1 <----- 시작 전 Thread ID와
0   <----- 이미 타이머 시작이 되었다.
Before ReadAsync : 4 <----- 완료 후 Thread ID가 다르다!!!
<?xml version="1.0" encoding="utf-8"?>
<History xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <Name>Yangbeng</Name>
  <Age>33</Age>
  <Friends>
    <string>범범조조</string>
    <string>쏭</string>
    <string>태발</string>
    <string>털</string>
    <string>쩌주</string>
  </Friends>
</History>
1
2
3
  • 위와 같이 파일을 읽을 때 까지 기다려 주지 않고, main 할 일을 진행하다가, 비동기 행동(FileRead)이 완료되는 것을 볼 수가 있습니다.

참고

https://staticvoidlife.tistory.com/92

'C# 문법' 카테고리의 다른 글

[C#] Class에서 인덱서[T] 사용하기  (0) 2022.01.04
[C#] 널 조건부 연산자 / 널 연산자  (0) 2021.12.29
[C#] Enum에 Name List / Value List 가져오기  (0) 2021.12.26
[C#] BackgroundWorker  (0) 2021.12.23
[C#] Delegate  (0) 2021.12.21