본문 바로가기
공부/Object-Oriented Design Pattern

Flyweight Pattern 플라이웨이트 패턴이란

by 혼밥맨 2021. 5. 26.
반응형

Flyweight Pattern 플라이웨이트 패턴이란

 

의도

Flyweight는 각 객체에 있는 모든 데이터를 유지하는 대신 여러 objects 간에 공통적인 상태 부분을 공유하여 더 많은 객체를 가용 RAM 크기에 맞출 수 있도록 하는 구조 설계 패턴입니다.

 

 

문제점

오랜 근무 시간 후에 재미를 느끼기 위해서, 여러분은 간단한 비디오 게임을 만들기로 결심했습니다: 플레이어들은 지도 주위를 돌아다니며 서로를 쏘고 있을 것입니다. 현실적인 시스템을 구현하여 게임의 고유한 기능으로 선택하셨습니다. 엄청난 양의 탄환과 미사일, 그리고 폭발로 인한 파편이 지도 전체에 날아가 선수에게 짜릿한 경험을 전달해야 한다.

이 작업이 완료되자마자 마지막 커밋을 추진하고 게임을 만든 다음 친구에게 테스트 드라이브를 보냈습니다. 비록 여러분의 기계에서 흠잡을 데 없이 게임이 실행되고 있었지만, 여러분의 친구는 오랫동안 게임을 할 수 없었습니다. 그의 컴퓨터에서는 몇 분간의 게임 플레이 후에 게임이 계속 중단되었다. 디버그 로그를 몇 시간 동안 파헤친 결과 RAM 용량이 부족하여 게임이 중단되었습니다. 알고 보니 당신 친구의 장비 성능이 당신 컴퓨터보다 훨씬 덜 강력했더군요. 그래서 그의 기계에서 문제가 그렇게 빨리 나타났죠.

실제 문제는 시스템과 관련이 있습니다. 총알, 미사일 또는 파편 조각과 같은 각 입자는 많은 데이터를 포함하는 별도의 물체로 표현되었다. 어느 순간, 플레이어의 화면에 나타난 대학살이 절정에 달했을 때, 새로 만들어진 입자들이 더 이상 남아 있는 RAM에 맞지 않아 프로그램이 다운되었다.

 

 

 

해결책

 

 Particle 클래스를 자세히 검사하면 색상과 스프라이트 (an image that represents the particle.) 필드가 다른 필드보다 훨씬 더 많은 메모리를 소모한다는 것을 알 수 있습니다. 더 나쁜 것은 이 두 분야가 모든 입자에 걸쳐 거의 동일한 데이터를 저장한다는 것입니다. 예를 들어, 모든 글머리 기호는 동일한 색상과 스프라이트를 가집니다.

 

coordinates, movement vector, and speed와 같은 particle 상태의 다른 부분은 각 particle마다 다르다. 결국, 이러한 필드의 값은 시간이 지남에 따라 변경됩니다. 이 데이터는 각 입자에 대해 색과 스프라이트가 일정하게 유지되는 동안 입자가 존재하는 항상 변화하는 컨텍스트를 나타냅니다.

개체의 이 상수 데이터를 일반적으로 고유 상태라고 합니다. 개체 내에 상주하며, 다른 개체는 읽을 수만 있고 변경할 수는 없습니다. 물체의 나머지 상태는, 종종 다른 물체에 의해 "외부에서" 변경되며, extrinsic state라고 불린다.

Flyweight 패턴은 개체 내부에 extrinsic state를 저장하는 것을 중지하는 것을 나타냅니다. 대신 이 상태를 이 상태에 의존하는 특정 메서드에 전달해야 합니다. 고유 상태만 개체 내에 남아 다른 컨텍스트에서 재사용할 수 있습니다. 따라서, 이러한 개체는 extrinsic보다 변동이 훨씬 적은 고유 상태에서만 다르기 때문에 더 적은 수의 개체가 필요합니다.

 

an object that only stores the intrinsic state is called a Flyweight pattern.

instrinsic state만을 저장하는 객체를 Flyweight pattern이라고 한다.

 

 

Extrinsic state storage
Extrinsic state는 어디로 이동합니까? 어떤 class에서 보관해야 하는 거죠? 대부분의 경우, 패턴을 적용하기 전에 개체를 집계하는 컨테이너 개체로 이동합니다.

우리의 경우, 이것이 particle 영역에 있는 모든 particle를 저장하는 주요 "Game" 객체입니다. Extrinsic state를 이 class로 이동하려면 각 입자의 좌표, 벡터 및 속도를 저장할 여러 배열 필드를 만들어야 합니다. 하지만 그게 다가 아니에요. particle를 나타내는 특정 Flyweight pattern에 대한 참조를 저장하기 위한 다른 배열이 필요합니다. 동일한 인덱스를 사용하여 particle의 모든 데이터에 액세스할 수 있도록 이러한 배열이 동기화되어야 합니다.

 

보다 더 나은 해결책은 flyweight object에 대한 참조와 함께 extrinsic state를 저장하는 별도의 context class를 만드는 것입니다. 이 방법을 사용하려면 container class에 단일 어레이만 있어야 합니다.

잠깐만! 이런 상황적 사물을 처음부터 가지고 있던 것만큼 많이 가지고 있어야 하지 않을까요? 엄밀히 말하면, 그렇습니다. 하지만 중요한 것은, 이 물체들은 이전보다 훨씬 더 작아졌다는 것입니다. 메모리가 가장 많이 사용되는 필드는 몇 개의 Flyweight object로 이동되었습니다. 이제 수천 개의 작은 상황별 개체는 데이터 복사본을 저장하는 대신 하나의 무거운 Flyweight object를 재사용할 수 있습니다.

 

 

플라이웨이트 패턴의 장점

  • You can save lots of RAM, assuming your program has tons of similar objects.

프로그램에 유사한 개체가 너무 많다고 가정할 때 RAM을 많이 저장할 수 있습니다.

 

 

플라이웨이트 패턴의 단점

 

  • You might be trading RAM over CPU cycles when some of the context data needs to be recalculated each time somebody calls a flyweight method.
  •  The code becomes much more complicated. New team members will always be wondering why the state of an entity was separated in such a way.
  • 누군가가 플라이웨이트 메서드를 호출할 때마다 컨텍스트 데이터 중 일부를 다시 계산해야 하는 경우 CPU 주기를 통해 RAM을 거래할 수 있습니다.
  •  그 코드는 훨씬 더 복잡해진다. 새로운 팀원들은 항상 왜 기업의 상태가 그런 식으로 분리되었는지 궁금해 할 것이다.


Prototype pattern vs Flyweight pattern

프로토타입 패턴 vs 플라이웨이트 패턴 차이점

 

 

1. 무엇보다도 위 두 패턴들은 각기 다른 범주에 속합니다: 프로토타입 패턴은 생성 패턴 중 하나이고, 플라이웨이트 패턴은 구조 패턴 중 하나입니다.

 

2. 프로토타입 객체의 생성은 복제를 거치며 객체의 생성을 용이하게 합니다. 복제 요청을 함으로써 매번 새로운 복제 개체를 만듭니다.

3. Flyweight에서는 개체를 공유하여 가능한 한 많이 재사용하려고 합니다. 이러한 개체를 찾지 못하면 새 필수 개체가 생성됩니다. 리소스 최적화를 위해 수행됩니다.

4. 프로토타입에서는 한 개체만 복제할 수 있지만, Flyweight 패턴은 애플리케이션에서 많은 개체를 사용할 때 사용하는 것이 좋습니다. While in Prototype we could clone even one object, Flyweight pattern makes sense to use when in the application we use big number of objects.

5. In Flyweight, object is immutable.
In Prototype, object is mutable.

6. Flyweight is about saving memory by not creating new objects and reusing existing ones when possible.
Prototype is about, reusing existing object in order to save cost of new object creation.

7. Flyweight is used when creating multiple type of single object.
Prototype is used when creating single type of single object.

 

플라이웨이트에서 물체는 불변이다.
프로토타입에서 객체는 돌연변이가 가능합니다.

Flyweight는 가능한 경우 새 객체를 만들지 않고 기존 객체를 재사용하여 메모리를 절약하는 것입니다.
프로토타입은 새로운 객체 생성 비용을 절약하기 위해 기존 객체를 재사용하는 것입니다.

Flyweight는 여러 유형의 단일 개체를 생성할 때 사용됩니다.
프로토타입은 단일 개체 유형을 생성할 때 사용됩니다.

반응형

댓글