0. 같이 보면 좋을 포스팅
"공유 메모리와 멀티 스레드의 이해" 포스팅에서 이어집니다.
[java 기초] 공유 메모리와 멀티 스레드의 이해
0. 이전 포스팅 : "멀티 스레드의 이해와 구현" 에서 이어지는 내용입니다. [java 기초] 멀티 스레드(Multi thread)의 이해 / 구현 1. 스레드(Thread) : 프로그램 / 프로세스 의 명령문을 위 → 아래로 차례
doinitright.tistory.com
저번 포스팅은 원론적인 얘기를 주로 다뤘으니 이번 포스팅에서는
구구절절 설명 않고 구현으로 바로 넘어가겠습니다.
1. 공유 메모리 및 공유 메모리를 활용할 스레드 구현
class SharedMemory extends Thread{
int x = 5;
boolean isQuit = false;
}
Thread를 상속받은 공유 메모리로 사용할 스레드인 `SharedMemory` 클래스를 만들어줍니다.
`SharedMemory` 클래스가 가지고 있으며, 스레드 간 메모리로 활용할 필드는 2개입니다.
- int형 변수 `x`: 초기값 세팅
- boolean형 변수 `isQuit` : 초기값 세팅
다음으로는 공유 메모리를 활용할 스레드 2개를 만들어줍니다.
class PlusThread extends Thread{
SharedMemory shmem; // 필드로 SharedMemory 클래스 인스턴스를 선언
/* shmem의 필드 변수 int x, boolean isQuit */
public void run(){
try{
while(!shmem.isQuit){ // shmem의 필드 isQuit이 false일 동안 loop
System.out.println("x = " + shmem.x);
Thread.sleep(300); // 300ms 경과 후
shmem.x++; // shmem의 필드 x값이 증가
}
} catch(Exception e){
System.out.println(e);
}
}
}
- `PlusThread`는 공유 메모리 스레드 `SharedMemory` 클래스 인스턴스 `shmem`을 생성해 내부 필드로 보유합니다.
- run() 메서드에서는 생성한 인스턴스 shmem의 필드인 int x에 대해 시간에 따라
- `x` 값 출력
- 300ms 시간 경과
- `x` 값 증가를 시킵니다.
- `PlusThread`는 프로그램 실행 후 공유 메모리의 `x` 값을 시간에 따라 증가시킵니다.
class MinusThread extends Thread{
SharedMemory shmem; // 필드로 SharedMemory 클래스 인스턴스를 선언
/* shmem의 필드 변수 int x, boolean isQuit */
public void run(){
Scanner sc = new Scanner(System.in); // User 입력을 위한 Scanner 호출
while(shmem.x!=0){ // shmem의 필드 x 값이 0이 아닐동안 loop
sc.nextLine(); // User가 Enter키 입력시
System.out.println("[System] Enter가 입력되었습니다.");
shmem.x--; // shmem의 필드 x 값 감소
}
shmem.isQuit = true; // shmem의 필드 x 값이 0 도달 시 필드 isQuit = true
System.out.println("[System] x값이 0입니다. 당신이 이겼습니다!");
}
}
- `MinusThread`는 공유 메모리 스레드 `SharedMemory `클래스 인스턴스 `shmem`을 생성해 내부 필드로 보유합니다.
- run() 메소드에서는 생성한 인스턴스 `shmem`의 필드인 int x에 대해 User의 입력에 따라
- `Scanner.nextln()` 으로 입력 생성
- 2. User가 `Enter` 입력 시 x 값 감소
- 3. x 값 0 도달 시 `isQuit = true`로 만들며 loop 종료
- `MinusThread`는 프로그램 실행 후 공유 메모리의 x값을 사용자의 입력에 따라 감소시킵니다.
마지막으로 메인을 구현해 만들어 놓은 스레드와 공유 메모리의 인스턴스를 생성하고,
이를 연결하겠습니다.
public class SharedMemoryTest {
public static void main(String[] args) {
PlusThread pt = new PlusThread(); // PlusThread 인스턴스 선언
MinusThread mt = new MinusThread(); // MiusThread 인스턴스 선언
SharedMemory shobj = new SharedMemory(); // SharedMemory 인스턴스 선언
/* 공유 메모리 연결 방법 : 공유 메모리 인스턴스 생성 후 각자 스레드 내부에
있는 필드 클래스를 공유 메모리로 참조 */
pt.shmem = shobj;
mt.shmem = shobj;
System.out.println("[System] x가 0이 될때까지 Enter키를 누르세요.");
// 스레드 클래스의 메소드 구현은 run(), 인스턴트 생성 후에 run() 호출은 start()로
pt.start();
mt.start();
}
}
2. 결과 1 : 사용자가 Enter를 입력하지 않을 시
[System] x가 0이 될때까지 Enter키를 누르세요.
x = 5
x = 6
x = 7
x = 8
x = 9
x = 10
/*
... 이후는 x가 무한 증가하는 loop
*/
3. 결과 2 : 사용자가 Enter 를 잘 입력했을 시
[System] x가 0이 될때까지 Enter키를 누르세요.
x = 5
x = 6
x = 7
[System] Enter가 입력되었습니다.
[System] Enter가 입력되었습니다.
x = 6
[System] Enter가 입력되었습니다.
[System] Enter가 입력되었습니다.
x = 5
[System] Enter가 입력되었습니다.
[System] Enter가 입력되었습니다.
[System] Enter가 입력되었습니다.
x = 3
[System] Enter가 입력되었습니다.
[System] Enter가 입력되었습니다.
x = 2
[System] Enter가 입력되었습니다.
[System] Enter가 입력되었습니다.
[System] x값이 0입니다. 당신이 이겼습니다!
보시다시피 Enter키 입력에 따른 x값이 감소하는 `MinusThread` ,
시간에 따라 x값이 증가하는 `PlusThread` 가 대립하며 작동하게 되고
열심히 사용자가 Enter를 연타해 x값을 0으로 만들면 종료되게 됩니다.
이 과정에서는 공유메모리 내의 필드인 int x와 boolean isQuit을 스레드가 공유하면서 작동함을 알 수 있습니다.
물론 static으로 정적 멤버를 선언해 공유 메모리를 대체해 동일하게 구현할 수 있으나,
추천되는 방법은 아닙니다.
'DEV > Java' 카테고리의 다른 글
[java 기초] Iterator 활용 ConcurrentModificationException 예외 해결 (0) | 2023.09.01 |
---|---|
[java] 코딩테스트 대비 java 클래스 별 메소드 정리 (1 / 2) (0) | 2023.08.23 |
[java] java 메모리 구조와 공유 메모리의 이해 (0) | 2023.08.04 |
[java] 멀티스레드(Multi thread)의 이해 / 구현 (0) | 2023.08.01 |
[java] java 객체의 직렬화와 역직렬화 (Serialization / Deserialization) (0) | 2023.07.30 |