ITEM 20 : Prefer Immutable Atomic Value Type
(변경불가능한 아토믹 값타입을 선호해라)
■ 요약 및 장점
+ 다른 곳에서 해당 type의 내부의 상태를 변경하기 못하게 하려면 immutable한 type을 선언해줘야 한다.
그것이 보장되지 않으면 내부의 상태를 변경하지 못하게 검사하는 비용이 많이 들어가게 된다.
여기에서는 초기에 생성된 후에는 변경되지 않게 보장하는 방법에 대해서 설명한다.
1. Immutable type은 생성된후에 변경하지 못하는 타입이다. 즉 상수(constant)이다.
2. Immutable type은 hash-based collection에서 더 잘 동작한다.
3. atomic type은 하나의 엔터티로 구성되어진 것을 말한다. 즉 더 쪼갤수 없는 단위를 말한다.
4. 아래의 예제는 변경을 하게 되면 유효하지 않는 데이터가 일시적으로 유지된다.
별 문제 없어 보이지만 만약에 멀티쓰레드 환경에서는 문제가 될수 있다.
즉, 한쪽에서 바꾸는 중간에 다른쪽에서 읽어 갈수 있기 때문이다.
// Mutable Address structure. public struct Address { private string state; private int zipCode; // Rely on the default system-generated // constructor. public string Line1 { get; set; } public string Line2 { get; set; } public string City { get; set; } public string State { get { return state; } set { ValidateState(value); state = value; } } public int ZipCode { get { return zipCode; } set { ValidateZip(value); zipCode = value; } } // other details omitted. } // Example usage: Address a1 = new Address(); a1.Line1 = "111 S. Main"; a1.City = "Anytown"; a1.State = "IL"; a1.ZipCode = 61111; // Modify: a1.City = "Ann Arbor"; // Zip, State invalid now. a1.ZipCode = 48103; // State still invalid now. a1.State = "MI"; // Now fine.
setter가 있기때문에 변경이 가능하긴하다. 다만 외부에서는 변경이 불가능하다.
public struct Address2 { // remaining details elided public string Line1 { get; private set; } public string Line2 { get; private set; } public string City { get; private set; } public string State { get; private set; } public int ZipCode { get; private set; } }
해당하는 멤버변수)를 readonly로 한정해줘야한다.
public string Line1 { get { return Line1; } } private readonly string line1;
7. immutable type을 선언할때 주의할점이 있다. 프로퍼티가 외부의 참조타입을 참조하면 외부에서 수정될 가능성이 존재한다.
public struct PhoneList { private readonly Phone[] phones; public PhoneList(Phone[] ph) { phones = ph; } public IEnumerable<Phone> Phones { get { return phones; } } } Phone[] phones = new Phone[10]; // initialize phones PhoneList pl = new PhoneList(phones); // Modify the phone list: // also modifies the internals of the (supposedly) // immutable object. phones[5] = Phone.GeneratePhoneNumber();
public PhoneList2(Phone[] ph) { phones = new Phone[ph.Length]; // Copies values because Phone is a value type. ph.CopyTo(phones, 0); }
■ Terms
■ 단어
Immutable:불변의,변경할 수 없는
validate:입증하다,인증하다,승인하다.
export:내보내다,수출하다.
invariant:변함없는,불변의
harmless:무해한.
fragment:조각,파편
specify:명시하다.
interim:중간의, 잠정적인
strictly:엄격하게
pitfall:함정,위험
'프로그래밍 > Effective C#' 카테고리의 다른 글
ITEM 19 : 값 타입에 대해서 0값이 유효한 상태가 되게 반드시 보장해야한다. (0) | 2015.04.30 |
---|---|
ITEM 18 : 값 타입과 참조 타임을 구별하라 (0) | 2015.04.23 |
ITEM 17 : 표준 Dispose 패턴을 구현하라 (0) | 2015.04.23 |
ITEM 16 : 불필요한 오브젝트 생성을 하지마라 (0) | 2015.04.23 |
ITEM 15 : 리소스 해제를 위해서 using과 try/finally 구문을 사용하라. (0) | 2014.05.30 |