인프런 커뮤니티 질문&답변

김도형님의 프로필 이미지
김도형

작성한 질문수

앨런 iOS Concurrency(동시성) - 디스패치큐와 오퍼레이션큐의 이해

4강에서요

작성

·

230

3

Serial 큐는 특정 하나의 스레드에서만 처리한다고 설명해주셨는데

제가 찾아보니 어떤 글에서는 특정 하나의 스레드가 아니라 한번에 하나의 스레드라고 하네요.

링크: https://stackoverflow.com/questions/51057441/serial-dispatch-queue-will-use-only-one-thread

,,,그래서 Serial 큐는 특정 하나의 스레드에서 처리하는게 맞는건가요?

답변 4

1

이런 미묘한 부분들에 대한 대화들이 저처럼 처음 학습하는 이들에게 있어 개념을 좀더 선명하게 잡는데 도움을 줍니다. 할 수 있는 의견 개진이고 수긍 가는 답변이라고 생각합니다. 두 분 모두 감사합니다.

1

앨런(Allen)님의 프로필 이미지
앨런(Allen)
지식공유자

네 도형님, 

말씀드렸듯이, 저는 저만 그렇게 생각한다고 말씀드리지 않았습니다. 많은 해외 자료들에서 그렇게 설명하고 있습니다. 

일단 해외자료들도 지금 다시 보니 (해외자료 들도 최근에 업데이트가 새로 되었고) 설명하는 자료가 꽤나 저와 유사한 방식으로 설명을 하던데, 
https://www.raywenderlich.com/9461083-ios-concurrency-with-gcd-and-operations/lessons/2

일단은 제가 캡처해 드린 화면을 보여드리겠습니다. 

일단 위의 자료는 레이웬더리치에서 GCD에서 SerialConcurrent큐를 설명하는 동영상 자료의 캡처 화면입니다. 참고해 보시면 좋을 것 같고,

또,
https://store.raywenderlich.com/products/concurrency-by-tutorials

의 책자에서는 23페이지에서 아래와 같이 기술하고 있습니다.


이렇게 자료로 보여드리는 이유는 제가 설명 내용을 임의대로 만든 것이 아니라는 것을 말씀드리기 위한 것입니다. 참고하여서 보시면 될 것 같고..

어쨌든 모든 개념을 원하시는 방식으로 이해하실때, 그것은 도형 님께서 판단해 보시면 될 것 같습니다.

메인 쓰레드/메인 큐시리얼입니다. 그렇다면 메인쓰레드는 하나의 쓰레드인가요? 아니면 한 번에 한개씩 여러개의 쓰레드에서 동작하는 쓰레드 인가요? 메인쓰레드는 하나의 쓰레드입니다. (만약 내부적으로 여러개의 쓰레드이고, 한번에 하나씩으로 동작한다고 하더라도 메인쓰레드를 하나의 직렬로 연결된 쓰레드라는 개념으로 머리속으로 이해하고 있는 것이 훨씬 낫다고 생각합니다. 그리고 저 뿐만이 아닌 모두가 그렇게 말하고 있습니다.)

그럼 메인 큐가 아닌 다른 커스텀 직렬(Serial) 큐들은 직렬(Serial)이지만 메인큐와는 다르게 (조금 다른 방식으로)여러개의 쓰레드에서 한번에 한개씩 동작하는 개념이라고...  메인큐와는 조금 다르게 별다른 개념이라고 머리속에 생각하여야 할까요? 저는 아니라고 생각합니다. (그렇게 되면 일관성이 떨어집니다.)

Serial이라는 말에서도 알 수 있듯이, 그냥 말그대로 해석해도 "직렬"(순차적/순서적)입니다. 그리고 Serial큐를 찾아보시면 "1) 한번에 하나씩 2) 순차적으로 실행" 한다고 설명하고 있습니다. 사실 여기서 개념적으로 좀 차이가 발생하는 것 같은데, 도형 님께서는 "한번에 하나씩"이라는 개념에 집중하시는 것처럼 보이고, 저는 "순차적으로 실행"이라는 개념이 더 중요하다고 봅니다. (왜냐면 비동기적으로 보내더라도 어쨌든 무조건 뒤에 들어가는 작업은 앞의 작업이 끝나길 기다릴 수 밖에 없으니까요.) (또 그리고 한개의 쓰레드라고 하더라도 당연히 한번에 하나씩 실행되는 개념을 벗어나지 않습니다.)

이제 아직 수강하지 않으신 후반부, 섹션 7의 2) 강의에서  Thread-safe한 개념에 대해서 다룰때, 직렬이면서 동기적인 내용 (Serial / Sync)이 나옵니다. (async 아님)

메인큐에서 동시큐로 보냈던 작업들을 다시 시리얼큐로 보내고, 때로는 Sync(동기적)으로 기다려서 실행하는 개념들이 나옵니다.  즉, (메인 ----> 동시 ----> 직렬 ) 이런식으로요. 그런데 도형님께서 말씀하신대로 여러개의 쓰레드에서 한번에 하나씩의 개념을 도입해 버리면 정말 엄청나게 헷갈릴 수 있습니다. (이 부분은 도형 님께서 후반부, 최소한 GCD 강의 내용을 다 들으신 후에 다시 말씀 하도록 하죠...)

네 어쨌든. 전 여러 해외의 자료들에서도 직렬큐는 하나의 쓰레드만 사용한다라고 말하고 있는데는 다 이유가 있다고 생각합니다.(저도 그 이유들에 대해서 공감하고요.) 그리고 이 부분에 대해서, 저는 저의 강의에서 GCD를 처음 접하시는 분들에게 오해를 사게끔 말하고 있다고 생각하지 않습니다. 다들 그렇게 말하고 개념적으로 생각하고, 그런 방식으로 동작하는 개념이라고 생각하고 있기 때문입니다. (전체적인 틀에서 이런 개념으로 이해하고, 세부적으로는 조금 다르게 동작한다라고 이해하는 것이 더 낫다고 생각하고, 처음부터 세부적으로 이해하고 그것을 응용하려면 더 어려워지는 개념에 가깝다고 봅니다.) 그리고 결론적으로 시리얼큐에서 우리 개발자가 사용하는 개념은 하나의 쓰레드로 이해하고 있는 편이 훨씬 낫다고 생각합니다. 쓰레드 객체를 직접생성해서 코드를 짜는 일은 없을 것이기 때문이죠.

네, 여러가지로 말씀을 드렸으니, 뒷부분 강의까지 들어보시고, 한번쯤은 왜 저와, 해외 다른 강의에서도 직렬큐는 한개의 쓰레드에서 동작하는 큐다라고 말하고 있는지 생각해 보시면 좋을 것 같네요. 그리고 그 부분에 대해서 도형 님께서 이해하고 싶으신 대로 이해하시는 것. 즉, 이제 도형 님의 몫이라고 생각합니다.

강의를 들어주셔서 감사합니다.

1

김도형님의 프로필 이미지
김도형
질문자

그래도 시리얼 큐는 하나의 쓰레드만 사용한다고 알려주시면 이 강의를 산 분들이 GCD 시리얼 큐에 대해 오해할 소지가 있다고 봅니다. 저는 단 한 번도 시리얼 큐에서 하나의 쓰레드만 동작한다고 생각하지 않았는데, 이 강의로 처음 GCD 큐를 접하신 분들은 그렇게 오해하실까 봐 질문 드렸습니다. ( 그리고 소프트웨어적인 스레드라 할지라도 주소값이 다 다르니 강의의 그림처럼 하나의 스레드에서만 처리하는 그림은 아닌 것 같습니다. )

그리고 시리얼 큐로 여러 개의 쓰레드가 한 번에 한 개씩 동작한다는 게 그렇게 어려운 개념은 또 아닌 것 같아요, 또 실제 동작한 대로 이해해야 하는 게 오해가 없으니 어려워도 원래 방식대로 설명하는 게 맞는 것 같고요.

답변 감사합니다. 강의 잘 보고 있습니다.

1

앨런(Allen)님의 프로필 이미지
앨런(Allen)
지식공유자

네 도형님 일단 이 부분을 설명 드리려면,

제가 강의에서 자세하게 설명 드리지 않은 부분을 설명 드려야 할 것 같은데요..^^

(사실 이 강의 내용을 이해하는 데 이부분까지 굳이 설명하면 더 헷갈리실 것 같아 설명드리지 않았습니다만,)

일단은 실제 CPU 코어에 있는 하드웨어적인 쓰레드가 있고,

우리가 앱을 실행할때 운영체제에서 생성하는 소프트웨어적인 쓰레드의 개념이 있습니다.

그리고 제가 그림을 그려서 강의에서 표현한 부분들은 사실 소프트웨어적인 쓰레드 입니다.

실제로 앱이 실행되면 운영체제는 하드웨어의 쓰레드 풀을 가져다가 필요한 소프트웨어적인 쓰레드를 생성했다가 필요없으면 없애고 하는 활동을 합니다. 그렇지만, 우리가 개발자로써 코드를 쓸때는 운영체제에서 다 알아서 해주니까 이부분을 신경 쓸 필요가 없는 부분이죠.. (실제로 GCD나 Operation큐에만 작업을 보내면 되니 알아서 해주기도 하고요.)

(굳이 쓰레드를 생성했다가 없앴다 하는 부분을 알아도 헷갈릴 것 같아서 강의에서도 말씀드리지 않았습니다.. 여러가지 개념을 이해하는 데 오히려 헷갈리는 부분이 생길 것 같아서요.. 아예 그냥 계속 존재하는 것처럼 생각하는 것이 전체적인 큰그림을 이해하는데 훨씬 도움이 된다고 생각하였습니다.)

위의 링크를 붙여주신 것과 같이 실제로는 한번에 하나의 쓰레드를 사용하는 것이 맞습니다. 그게 실제로는 하드웨어적인 여러개의 쓰레드 일수도 있겠지요. 다만, 우리가 개념적으로 시리얼큐가 (한번에 한개이긴 하지만) 여러개의 쓰레드를 사용한다고 생각이나 개념을 잡아 버리면.. 제 생각에는 너무 어려울 것 같습니다.......... (순서적으로 어떻게 실행할 수 있지? 이런 생각이 들기도 하고요.. Serial이라는 영어 단어 자체가 직렬이라는 말입니다. 영어 그대로 생각해보시면 되고, 왜 그렇게 이름을 지었을까요?)


이런 부분들을 고려해서,

저만 이렇게 생각하고 있는 것이 아니라..

해외 자료들에서도 이론적으로는 Serial큐는 하나의 쓰레드에서만 순서적으로 처리한다고 설명하고 있습니다.

(앱을 실행할때 특정하는 메인쓰레드조차도, 어쩌면 하드웨어적으로 여러쓰레드를 사용할지도 모릅니다. 하지만, 아무도 메인쓰레드가 한번에 하나의 쓰레드를 사용하는 개념이라고 생각하지 않지요..)

개념적으로 더 잘 이해하고, 더 잘 사용하기 위해서 시리얼큐는 하나의 쓰레드만 사용하는..  제가 그려드린 그림 방식대로 이해하는 것이 더 낫지 않을까? 생각해봅니다.

실제 동작과 우리가 이해해야하는 개념과는 조금 차이가 있다고 봅니다. ^^

좋은 질문들 고맙습니다. :)

김도형님의 프로필 이미지
김도형

작성한 질문수

질문하기