달력

12

« 2024/12 »

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31

Thread란 뭘까? 


책에서 스레드 관련 목차를 보면 

1.프로세스와 쓰레드 //그냥 쓰레드랑 멀티쓰레드를 한번에 묶어서 설명한 책도있다.!  

2. 쓰레드의 구현과 실행 

3.싱글쓰레드와 멀티쓰레드 

이후에 쓰레드의 우선순위, 쓰레드의 그룹, 데몬쓰레드 실행제어 동기화등이 설명되어있다.



예전에 한번 블로그에서 동기화에 관해서 앞부분만 설명했는데 오늘은 쓰레드에 관해서 정의나 앞에 전반적인 부분에 대해서 설명하려고 한다. 언어는 볼때마다 기분이 새롭다 ~_~ 




Thread는 한글로 직역하면 '실'이다. 바느질할때 사용하는 ! 

바늘에 실을 꿰어놓으면 오직 그 하나의 실로 하나의 작업을 할 수 있다. 만약에 내가 실로 두가지 바느질을 동시에 하려면 실(thread)가 따로 필요하다.  


컴퓨터 용어로 사용되는 스레드는 실의 의미와 일맥상통한다. 

--> 자바에서 상속부분에서 extends는 확장하다 라는의미인데 조상클래스에서 자식클래스로 갈수록 확장한다는 개념에서 extends라는 단어를 받아들이면 용어가 이해하기 더 쉬운데 스레드도 그런 의미해서 이해하면 더 받아들이기 쉽다. 


컴퓨터에서 사용하는 스레드(thread)는 thread of control의 준말로. 프로그램 코드를 이용하면서 실행하는 하나의 실 

혹은 제어의 개념이다. 아까 말한것처럼. 하나의 실로 하나의 바느질 밖에 할 수 없듯이 하나의 스레드로 하나의 작업밖에 처리할 수 없다. 


쓰레드 부분을 공부하면  프로세스에 대해서도 알고있으면 좋은데.. 


그전에 

프로세스와 프로그램의 차이를 알고있어야한다.

사실 여기서 운영체제(OS) 부분으로 들어가면 프로그램과 프로세스 차이에 대해 더 자세하게 정리할수있지만..

나는 쓰레드에서 프로세스와 프로그램의 차이를 간단하게 집고 넘어갈꺼라 추후에 정리하도록 하겠다.


  • 프로그램(Program) -->실행 가능한 파일
  • 프로세스(Process) -->실행 중인(Running) 프로그램(메모리)


이렇게 프로그램을 --->(실행)하면  --> 프로세스 


프로세스는: 실행중인 프로그램을 말한다. 자원(resources)과 쓰레드로 구성된다. 

쓰레드 : 프로세스 내에서 실제 작업을 수행한다. 모든 프로세스는 하나 이상의 쓰레드를 가지고있다.


쓰레드한마디로 말하자면 실행의 단위이다. 


프로세스가 공장이라면.. 쓰레드는 일꾼이랄까 


모든 프로세스에는 최소한 하나 이상의 쓰레드가 존재한다. 

둘 이상의 쓰레드를 가진 프로세스를 (Multi-threaded process)라고한다. 


하나의 프로세스가 가질 수 있는 쓰레드의 개수는 제한되있지는 않으나. 

쓰레드가 작업을 수행하는데 개별적인 메모리 공간(호출 스택)을 필요로 하기 때문에 

프로세스 메모리 한계에 따라 생성할 수 있는 쓰레드 수가 결정된다.

(근데 실제로 그정도로 많은 쓰레드를 생성하는 일은 없을거다 ㅋㅅㅋ)


멀티프로세스(multi-processing)와 멀티쓰레드(multi-threading)를 비교하자면. 

하나의 새로운 프로세스를 생성하는 것보다 하나의 새로운 쓰레드를 생성하는게 

더 적은 비용이 든다.  그러나 멀티쓰레드도 단점이있다. 그건 아래에 정리하겠다 ! 


---> 멀티프로세스는 하나의 응용프로그램이 여러 개의 프로세스(process)로 구성하여 각 프로세스가 

하나의 작업(task)를 처리하도록 하는 기법이다. 


위에 그림처럼 각 프로세스는 고유한 메모리 영역을 독립적으로 실행된다. 그러므로 하나의 응용프로그램에 속하는 프로세스들조차 상호통신 오버헤드가 크고 프로세스의 문맥교환(context switch)에 따른 과도한 작업량과 시간 소모의 문제점이 있다. (밑줄친 부분을 몰라도 괜찮다. 자바 예제 하는데 지장없다.)


이러한 문제점을 개선하기 위해 제안된 방법이 멀티스레드다!! 


---> 멀티스레드는 하나의 응용프로그램을 여러 개의 스레드로 구성하고 각 스레드로 하여금 하나의 작업을 처리하도록 하는 기법이다.


모든 스레드가 응용프로그램 내의 자원과 메모리를 공유하므로 통신에 따른 오버헤드가 비교적 크지 않고, 스레드 사이의 문맥교환 시에 작업량이 작고 시간이 짧은 장점을 지닌다. 

멀티스레딩시에 운영체제의 스케쥴링 단위가 스레드인셈이다. 


윈도우나 리눅스등 많은 os가 멀티프로세스를 지원하고 있지만 멀티스레드을 기본으로 하고있다. 


멀티쓰레드의 장단점을 얘기하자면 


<장점>

-자원을 보다 효율적으로 사용가능

-사용자에 대한 응답성(response)가 향상

-작업이 분리되어 코드가 간결 


--> 여러모로 좋다!


<단점>

-동기화(synchronization)에 주의해야한다. 

-교착상태(dead-lock)가 발생하지 않도록 주의해야 한다.

-각 쓰레드가 효율적으로 고르게 실행될 수 있게 해야하낟.


-->프로그래밍할때 고려해야할 사항들이 많다.

 




우리는 자바에서 스레드로 작동할 코드만 준비하면되고, 스레드의 실행을 책임지는건 JVM이다.

-->자바스레드(java thread)는 JVM에 의해 스케줄되는 실행단위의 코드블록이다. 


자바에서 jvm(자바 가상 머신)은 멀티스레드를 지원하기때문에 자바 응용프로그램은 하나 이상의 스레드를 생성할수있다. 스레드가 생성되면 스레드에 관련된 정보 (Thread Control Block, TCB)가 생성되는데 JVM이 관리한다.


JVM은 (1)한개의 응요프로그램만 실행 가능하다. -->여러개 응용프로그램 실행 불가 X 

    (2)하나의 응용프로그램이 여러 개의 스레드를 가질 수 있다.! 


우리는 이제 이 스레드를 어떻게 사용할지 만드는 방법에 대해서 알고있으면 된다!  구현하는 방법! 





이번 내용을 통해서 내가 결론적으로 말하고싶은건


  • 쓰레드라는건 실행의 단위이고(실!!! ) 

  • 프로세스와 프로그램, 멀티프로세스와 멀티쓰레드의 차이를 알았다는거 !! 

  • 멀티쓰레딩을 이용하여 프로그램 실행시에 장점과 단점이 있기에 고려를 해야한다는점 

  • 그리고 자바에서 스레드의 실행을 책임지는건 JVM이기 때문에 우리는 

    작동시킬 코드만 준비하면 된다는 점이다. 


--> 다음번에는  스레드 구현에 대해서 설명하겠다. 





  


그림 출처: -http://good-dba.tistory.com/9 -->티스토리 

              -자바의정석 PPT 참고 !! 




:
Posted by Gongdile

쓰레드의 동기화(synchronization)이란 뭘까? 

--> 한스레드가 진행중인 작업을 다른 쓰레드가 간석하지 못하도록 막는것을 말한다.


왜쓸까? 


싱글스레드 프로세스 경우는 프로세스 내에서 단하나의 스레드만 작업하기 때문에 

프로세스의 자원을 가지고 작업하는데 별 문제가 없다. 


하지만 

멀티스레드의경우에는 여러 스레드가 같은 프로세스 내의 자원을 공유해서 작업하기 때문에 

서로의 작업에 영향을 주게된다. 


예를들면 

ATM에 통장에 50만원이있었는데 각 다른 두곳에서 출금한다고 가정하자 ㅋㅋ 

동시에 두곳에서 50만원이 출금되면 정말 행복하겟지만.. 

은행입장에서는 큰일나는거 아닌가 ..ㅋㅋㅋ 


A atm기에서 작업을 실행할대 락을 걸어서 다른 곳은 접근못하게하고 출금이 다끝난뒤에 

접근권을 획득해서 B atm기가 출금해야 이중으로 출금되는것을 막을수있다. 

--------------------------------------------------------------------------------------------


그래서 스레드에서는 저런 일이 방지하는것을 막기위해서


한 쓰레드가 특정 작업을 끝마치기 전까지 다른 쓰레드에 의해 방해받지 않도록 하는것이 필요한데


그래서 도입된 개념이 '임계 영역(critical section)'과 '잠금(락,lock)'이다.


->공유 데이터를 사용하는 코드 영역을 임계 영역으로 지정해놓고, 공유 데이터(객체)가 

가지고 있는 lock을 획득한 단 하나의 쓰레드만 이 영역 내의 코드를 수행할 수 있게 한다.

그리고 해당 쓰레드가  임계 영역 내의; 모든 코드를 수행하고 벗어나서 lock을 반납해야만 

다른 쓰레드가 반납된 lock을 획득하여 임계 영역의 코드를 수행할 수 있게 된다. 


-------------->위에서 말한것처럼 이런 한 쓰레드가 진행 중인 작업을 다른 쓰레드가 간석하지 못하도록 막는것을!! 

'쓰레드의 동기화(Synchronization)' 라고 한다.   


동기화 방법에는 여러가지가있다. synchronized를 이용한 방식, wait ( ) , notify( ) , notifyAll( ) 를 이용한 방식.. 

여러가지가있는데 오늘은  synchronized를 이용한 방식에 대해 설명할 예정이다.. 

(여러개를 포스팅하고싶지만.. 힘들다 ㅠㅠ 조금이라도 꾸준히 올리는게 목표다)


1.synchronized를 이용한 동기화 


가장 간단한 동기화 방법인 synchronized 키워드를 이용한 동기화에 대해서 알아보면 

이 키워드는 임계 영역을 설정하는데 사용된다. -->두가지 방식이있다. (사진이 생각보다 짱큰게 올라갔다)


<첫 번째 방법>

메서드 앞에 synchronized를 붙이는방법 

synchronized를 붙이면 메서드 전체가 임계영역으로설정된다. 

쓰레드는 synchronized메서드가 호출된 시점부터 해당 메서드가 포함된 객체의 lock을 얻어 작업을 수행한다.

메서드가 종료되면 lock을 반환한다.


<두 번째 방법>

메서드 내의 코드 일부를 블럭 { }으로 감사고 블럭 앞에 'synchronized(참조변수)'를 붙이는 방법

이때 참조변수는 --> 락을 걸고자하는 객체를 참조하는것이어야한다. 


이 {  }블럭을 synchronized블럭이라고 한다. 

->이 블럭의 영역 안으로 들어가면서부터 쓰레드는 지정된 객체의 lock을 얻게되고. 

   블럭을 벗어나면 lock을 반납한다.


-----------

두 방법 모두 lock을 하나씩 가지고 있다.

해당 객체의 lock을 가지고 있는 쓰레드만 임계 영역의 코드를 수행할 수 있다.

그리고 다른 쓰레드들은 lock을 얻을 때가지 기다리게 된다.

------

임계 영역은 멀티쓰레드 프로그램의 성능을 좌우하기 때문에 가능하면 메서드 전체에 락을 거는것보다 

synchronized블럭으로 임계 영역을 최소화해서 효율적인 프로그램이 되도록 노력하는게 좋다.



아래는 synchronized 사용예제에 대해서 설명할거다 


쓰레드 동기화를 사용한 경우와 사용하지 않은 경우의 차이를 간단한 예제를 통해서 설명하려고한다.


공쓰레드와 다일쓰레드가 사용하는 부분을 보여줄 예정이다. 



위에 소스는 

gong과 dile이라는 이름의 스레드를 생성하여 집계판에 동시에 접근하게 한것이다. 

그리고 두 스레드를 실행시키는 부분이다. 


위에 소스와 이어서 타이핑 친부분이다 아래는 

공유 데이터인 집계판을 시물레이션하는 클래스를 만든거다.

이제 아래 소스를 보자 


최종적으로 소스에 흐름에 대해서 설명하자면 


SyncObject멤버 add( )를 synchronized 메소드로 지정했다. 

왜??!

-->add ( )는 두명의 gong,dile 즉 WorkerThread 스레드가 동시에 호출할수있는 임계영역이기 때문이다.

    또한 add( ) 메소드는 sum 공유변수에 접근하고 있기 때문이다. 


WorkerThread는 루프를 돌면서 27번줄에 SyncObject의 add( )메소드를 호출하여 

SyncObject의 sum 멤버 값에 10을 더하고 리턴한다. 

main은 이름이 "gong","dile"인 두개의 WorkerThread 스레드를 생성한다. 


최종 sum이 얼마일꺼같나? ㅋㅋ -->200이다!! 왜??1 

gong와 dile이가 각각 10번씩 add( )를 호출했기때문에 

동기화가 잘이루어진다면 최종 누적점수 sum이 200이 된다. 


그림으로 표현하면 이렇다.. 


어떤 형식으로 찍힐까?

이런식으로 gong과 dile이가 순차적으로 sum되가면서 찍힌다. 


근데 만약에 synchronized키워드를 제거하게 되면 어떻게 출력될까?


실행할때마다 다르긴한데  충돌이된 예시를 보여주자면 


위에 네모박스처럼 add( ) 메소드에 충돌이 생긴경우다

-->이때문에 10이 증가되지못했다.


아래 밑줄처럼 두 스레드의 add(  ) 메소드에 대한 동시 실행으로 인해 190밖에 도달하지 못했다.


근데 저 코드를 맨날 실행한다고 같은 결과가 나오는건 아니다 

여러번 충돌할수도있는거고 충돌안할수도있는거고 하지만 동기화를 해주지 않으면

충돌할 위험이 있기 때문에 해줘야한다. 


두개의 스레드가 동시에 호출할 경우가 발생할 위험이있기때문에 동기화 처리를 해주는거다. 


2.wait( )과 notify( )를 이용한 방식 은 나중에 정리하겠다!! 


:
Posted by Gongdile