일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | 4 | |||
5 | 6 | 7 | 8 | 9 | 10 | 11 |
12 | 13 | 14 | 15 | 16 | 17 | 18 |
19 | 20 | 21 | 22 | 23 | 24 | 25 |
26 | 27 | 28 | 29 | 30 | 31 |
- UITextView
- uiscrollview
- 리팩토링
- Observable
- RxCocoa
- swift documentation
- 애니메이션
- Clean Code
- rxswift
- Protocol
- UICollectionView
- SWIFT
- 스위프트
- ribs
- uitableview
- swiftUI
- ios
- 클린 코드
- Xcode
- Human interface guide
- 리펙토링
- collectionview
- MVVM
- map
- clean architecture
- combine
- HIG
- 리펙터링
- tableView
- Refactoring
- Today
- Total
목록Refactoring (리펙토링) (58)
김종권의 iOS 앱 개발 알아가기
질의 함수와 변경 함수 분리하기 용어 질의 함수: 데이터를 단순히 가져오는 함수 (getter) 변경 함수: 데이터를 변경하는 함수 (setter) 함수를 구현할 때, side effect가 없이 값을 반환해주어야 하는 함수를 추구해야함 이유) side effect가 없는 함수를 사용할 때 개발자가 신경 쓸 것들이 없는 장점이 존재 side effect가 없다면 어느 때건 원하는 만큼 호출해도 아무 문제가 없으며 호출하는 문장의 위치를 호출하는 함수 안 어디로든 옮겨도 되며 테스트하기도 용이 질의 함수, getter 연산 프로퍼티에서는 side effect가 없게 구현해야함 질의 함수와 변경 함수 분리하기 예제 Product라는 구조체가 있고, items를 갖고 있는 상태 removeAndGetRemai..
Assertion 추가하기 특정 조건이 참일 때만 동작하도록 하는 코드 영역이 있는데, 이러한 기능을 development 타겟에만 적용시켜서, 사전에 개발할 때 실수를 방지하도록 하는 기능 이러한 가정이 코드에 항상 명시적으로 기술되어 있지 않거나 이런 명시적인 것을 못보고 개발을 할 때 실수를 막기 위하여 assertion을 넣는 것 assertion 추가 시 주의사항 assertion 실패는 시스템의 다른 부분에 영향을 주지 않아야함 development 타겟에만 적용시켜 운영에서는 영향을 주지 않도록 해야함 assertion은 개발자가 실수를 할만한 곳이나 버그를 잡은 후에도 assertion을 넣으면 다른 개발자가 실수할 확률을 줄어주기 때문에 좋은 코드 Assertion 리펙토링하기 swift..
조건부 로직을 protocol로 바꾸기 이전 포스팅 글에서는 switch case 조건부 로직을 다형성으로 바꿨었는데, 상속을 사용하게되면 코드를 파악하기 어렵고 수정하기 어려운 반면에 protocol을 사용하면 이전 포스팅 글에서 알아본 대로 여러 이점이 존재 (아래 "Protocol 프로그래밍을 지향해야하는 이유"요약 참고) Protocol 프로그래밍을 지향해야하는 이유 *protocol = 자바의 Interface DIP (Dependency Inversion Principle): 소스코드 의존성이 구현체에 의존하지 않고 추상(protocol)에 의존하는 것 DIP 구체적인 개념은 이전 포스팅 글 참고 기능제공(=확장성) 확장성이라는 의미는 개발자가 코드를 작성할 때 매우 자연스럽게 사용이 가능 사..
조건부 로직을 다형성으로 바꾸기 조건부 로직이 복잡해지면 수정하기가 굉장히 어려워지므로, 더 높은 수준의 개념인 다형성을 사용하여 조건들을 분리하는 방법 switch 문 안의 case가 여러개 있을 때 case별로 클래스를 하나씩 만들어서 공통 switch 로직의 중복을 제거하는 것이 목표 특히 switch case로 나누어진 분기 부분들에서 조건부 로직을 자신만의 방식으로 처리하도록 구성할 때, 다형성을 사용하여 각 클래스에서 처리하도록하면 SRP(Single Responsibility Principle) 원칙도 지키는 효과 조건부 로직을 다형성으로 바꾸기 예시 리펙토링 전) 사용자가 맥주를 고르고 이 맥주의 가격을 측정하는 프로그램 맥주의 종류는 enum으로 정의된 상태 각 맥주의 가격이 각각 다름 ..
중첩 조건문을 보호 구문으로 바꾸기 중첩 조건문이 많이 들어있는 케이스는 코딩을 하다보면 흔하게 발생하는데, 중첩이 되는 순간 깊이가 깊어지면서 읽기가 어려운 코드가 됨 if와 else 구문이 있을 때, if절과 else절은 똑같은 무게를 두어서 코드를 읽는 이에게 양 갈래가 똑같이 중요하다는 암시적인 의미를 전달하는데, 짧은 중첩 조건문이 있을땐 보호 구문으로 바꾸는게 좋음 swift의 guard와 같은 보호 구문으로 변경하면, 이건 이 함수의 핵심이 아니고, 이 일이 일어나면 무언가 조치를 취한 후 함수에서 빠져나온다는 의미를 전달예제 swift에만 있는 guard문 키워드가 탄생한 이유 보호구문 리펙토링의 핵심은 함수 내부의 의도를 부각하는 것 중첩 조건문을 보호구문으로 변경하기 예제 리펙토링 전)..
조건문 통합하기 비교하는 조건이 다르지만 그 결과로 수행하는 동작들에 대해서 조건부 코드를 나누지 말고 하나로 통합하는 것 리펙토링 전) struct Employee { let salary: Int let month: Int let isPartTime: Bool } let employee1 = Employee(salary: 3, month: 12, isPartTime: false) // Refactoring 전 func returnSome() -> Int { if employee1.salary > 2 { return 0 } if employee1.month > 5 { return 0 } if employee1.isPartTime { return 0 } return 1 } 리펙토링 후) func someC..
조건문 분해하기 조건문에서 중요한 것 조건문에서 무슨 일이 일어나는지 이야기해주지만 '왜'가 들어나는 코드가 필요 조건문들을 함수로 만들어서 조건의 의도가 분명하게 들어나도록 수정이 필요 // '어떻게'만 나타난 조건문 - 조건문이 길어지게되면, 조거문 안에 블록문에서 일어나는 이유를 파악하기가 힘듦 if 20 < jake.age && jake.plan.summerStart < jake.plan.reservationDate { charge = basePrice * 2 } else { charge = basePrice } // '왜'의 의미가 있는 있는 조건문 - 조건문을 추상화하여, 조건문 안에 charge = basePrice * 2의 이유를 파악하기 쉬움 if adult() && summer() { ..
값을 참조로 바꾸기 개념 데이터를 공유해야하는 상황에서는 모델을 참조 타입으로 변경 데이터를 공유해야할때, 만약 값 타입을 사용하고 있다면 그 데이터를 변경하면 그 데이터의 모든 복제본을 찾아서 빠짐없이 갱신해주는 번거로움이 존재 갱신해주다가 만약 하나라도 놓치면 데이터의 일관성이 깨져버리는 현상이 발생 값을 참조로 바꾸게 되면 *엔티티(Entity) 하나당 객체도 단 하나만 존재하며, 이런 객체들을 한데 모아 놓고 클라이언트 코드(사용하는 쪽의 코드)들이 접근을 관리해주는 일종의 저장소가 필요 엔터티(Entity): 식별 가능한 개체 ex) 고객이라는 Entity에는 이름, 나이, 주소와 같은 Attribute를 갖음 값을 참조로 바꾸기 리펙토링 해보기 ex) Order 모델 안에 Customer가 있..