[059] 플러터 (Flutter) 배우기 - immutable 객체 사용하기

2023. 4. 27. 14:52모바일어플개발/Flutter

반응형

안녕하세요~ totally 개발자입니다.

 

immutable

 

이번 시간에는 플러터에 사용되는 Dart 강좌로 오늘은 immutable 객체에 대해서 살펴보도록 하겠습니다. immutable 말그대로 "불변의, 변경할 수 없는"이라는 뜻으로 쓰입니다. 

immutable를 쓰기에 앞서 이 부분을 왜 작성하는지를 살펴볼 필요가 있습니다.

 

먼저 아래와 같은 코드가 있다고 가정합니다. 스타크래프트 마린의 객체를 정의한 예제 클래스이고 17-18번째 줄에 마린 한 마리를 인스턴스화 해주었습니다. 

 

여기에서 중요한 부분은 26-28번째 줄에 마린을 매개변수로 받아 마린의 공격력을 50 더해주는 함수를 선언했고 그 선언된 함수를 21번째 줄에서 호출하여 사용했습니다. 

 

테스트해본 결과입니다. 여기서 marine1을 직접 변경한 것은 아니고 marine 매개변수를 참조하여 변경하는 모습인데 이것은 권장되는 방법이 결코 아닙니다. 이 예시에서는 코드가 단순하다 보니 직관적으로 파악할 수 있지만 코드가 복잡해지다보면 분명히 이런 값이 나와야 하는데 다른 값이 도출되는 현상이 발생할 수 있기 때문입니다. 이를 방지하기 위한 방법 중 하나가 final 키워드와 immutable annotation을 사용하여 방지할 수 있습니다.

 

 

 

이렇게 작성하시면 더 이상 attackDamage를 마음대로 조작할 수 없음을 확인해볼 수 있습니다. 위에 because it's final이라고 명시되어 있기 때문입니다. 그렇다면 이 마린의 공격력을 혹시 변경해야 하는 경우에는 어떻게 변경해야 할까요? 바로 새로운 객체를 만들어주어야 합니다. 

 

위의 스크린샷에 보시면 import 'package:meta/meta.dart';을 작성해주시고 (이렇게 하셔야 dart test.dart로 실행이 됩니다) 그 다음 copyWith 함수를 적어줍니다. 

 

그 후에 marine1.copyWith로 새롭게 id와 attackDamage를 정의해주면 됩니다.

 

테스트한 결과입니다. 이렇게 객체를 복사해서 하나를 더 만들어주는 것이 좋습니다. 이렇게 한다면 기존의 marine1의 데이터는 조작될 수 없는 데이터로 신뢰할 수 있게 되고 marine1을 직접적으로 건드리는 코드는 컴파일 과정에서 오류를 잡아낼 수 있기 때문에 유용하게 사용될 수 있습니다. copyWIth 이외에 직접 마린 객체를 모든 인스턴스 변수들을 포함하여 깊게 복사(deep copy)해야 하는 경우가 많을텐데 이 경우를 위해 deepCopy 메소드도 작성해주도록 하겠습니다. 

 

이 deepCopy 메소드는 간단히 인스턴스를 복사해서 새 인스턴스를 반환해주는 용도입니다. 

 

위에 보시면 marine1.deepCopy() 호출하여 marine3의 인스턴스를 생성할 수 있습니다. 물론 이런 용도로도 쓰일 수 있지만 다른 함수의 파라미터로 전달할 때 이 복사한 것을 파라미터로 전달할 때에도 이렇게 사용될 수 있습니다. 복사해서 전달하게 되면 다른 클래스에 의해 영향을 받지 않고 자신이 속한 클래스 내에서는 신뢰할 수 있는 데이터를 가지는 유효한 값을 지니게 됩니다. 이 immutable 객체를 이해해야 하는 이유는 그 다음 포스팅에서 살펴볼 freezed에 대해 사전 이해가 필요하기 때문이고 이 개념을 실제로 사용하지는 않는다 하더라도 이 부분에 대한 이해가 있다면 실제 개발하는 데에 도움을 줄 수 있으리라 생각합니다.

 

[전체 소스 코드]

 

 

반응형