골라밥 프로젝트를 하다가, 뷰 전환에 대해서 좀 고민을 많이했다.
원래 상태는 다음과 같다.
이렇게 3개의 뷰에서 2번뷰에서 버튼을 누르면 1번뷰로 2번뷰를 제거 한다음 3번뷰를 push해주는 방식이었다.
여기에서 처음에 생각한 방법은 delegate패턴을 사용해서 2번뷰에서 클릭이벤트 발생시 1번에서 감지하여 3번을 띄워주는 방법이었는데
이를 사용하자니, 2번뷰가 dismiss되는부분에서 delegate가 정상적으로 작동하지 않았다.
따라서 나는 어쩌피 3개의 뷰에서 계속 상태를 체크해야하기 때문에, 싱글톤 객체를 통해서 상태값을 저장하는것으로
2번뷰에서 버튼을 누르면 dismiss하고, 1번뷰에서 willappear에서 체크를하여서 3번뷰를 띄워주는 방식을 채택하였다.
여기에서 3번뷰에서는 willappear에서 다시 싱글톤객체에 접근하여 해당 값을 변경해주는 것으로 상태값을 리셋해준다.
이 외에도 코디네이터 패턴이나, viper를 이용하여 해당 문제를 해결할수 있다고는 하였지만, 당장에 리팩토링을 하기에는 마땅치 않았으며, 해당 패턴에 대한 이해가 좋지 않기때문에 가장 쉽게 할수있는 싱글톤을 이용하였다.
싱글톤의 단점
- 싱글톤 패턴은 전역적인 상태를 유지하기 때문에, 다른 클래스나 모듈과의 결합도가 높아질 수 있다. 이는 유닛 테스트를 어렵게 만들고, 유지보수성을 저하시킬 수 있다.
- 멀티스레드 환경에서 사용할 경우 동기화 문제가 발생할 수 있다. 만약 멀티스레드 환경에서 동시에 해당 인스턴스를 사용하려는 경우, 예기치 않은 결과가 발생할 수 있다.
- 싱글톤 인스턴스는 프로그램이 시작될 때 생성되므로, 필요하지 않은 경우에도 자원을 사용하게 됩니다. 이는 성능 저하를 초래할 수 있다.
- 싱글톤 패턴은 하나의 인스턴스만 존재하기 때문에, 이를 상속하여 새로운 인스턴스를 생성하는 것이 불가능합니다. 이는 유연성을 저하시킬 수 있다.
여기에서 내가 집중한 단점은 클래스나 모듈에 결합도가 너무 높다는 점이었다.
따라서 이를 해결하기 위한 방법을 찾아보다가 Protocol을 이용하면 이를 해결할수 있다는것을 동료 개발자에게 듣게 되었다.
타입으로 사용하는 Protocol
프로토콜을 사용하는 것으로, 클래스 내부에서 해당 프로퍼티가 싱글톤 객체인지 인식하지 못하게 하는것으로 결합도를 줄일수 있다.
다음은 이를 이용한 간단한 예시이다.
동일하게 이러한 뷰가 있다고 정의하고 해당 뷰에서는 하나의 버튼과 라벨이 존재한다.
1번 뷰에서 2번으로 갈때 2라는숫자를 , 2번에서 3으로갈때는 3이라는 숫자를 세팅하는것으로 데이터를 싱글톤으로 옮긴다고 가정한다.
기존의 코드
기존의 코드에서는 다음과 같이 싱글톤을 직접 접근하게 된다.
Datas.shared.number = 1
Datas.shared.number = 2
Datas.shared.number = 3
각 이전 뷰에서 버튼이 눌릴때 이렇게 싱글톤 객체에 접근하여 값을 변경하게 된다.
의존성 해결
1. 모델구조
우선 싱글톤 객체 모델을 다음과 같이 만든다.
싱글톤은 DataProtocol을 준수하게 되고, number은 get set을 가진 연산 프로퍼티이다.
이를통해서 다른 클래스에서 numbe의 값에 접근하고, 변경이 가능하게 된다.
2. 프로토콜을 타입으로 받는 변수 선언
data는 DataProtocol 타입이다!.
이를 통해서 mainView에서 객체를 주입해주면, secondView에서는 해당 data라는 프로퍼티가 싱글톤 객체라고 인식을 할수가 없다. 이를 통해서 좀더 유닛테스트를 용이하게 한다.
Uploaded by N2T