오늘 한 일.
프로그래머스 2문제를 풀었다.
iOS 학습
자료구조 학습
새로 배운 것.
- mutating 사용법과 사용하는 이유
- 구조체나 열거형의 인스턴스 메소드 내에서 프로퍼티의 값을 변경할 수 없는데, 이 때 인스턴스 메서드의 prefix로
mutating
을 사용하면 해당 프로퍼티에 새로운 값을 생성해서 대치시키면 값을 변경할 수 있게된다.
- 클래스와 프로토콜의 차이점 중 하나는 다중상속 여부다.
- UserDefaults로 데이터를 사용자 정의 타입으로 저장할 경우 Data 타입으로 변경하여 저장해야 한다. 예를 들어, 구조체는 객체를 Data 형식의 바이트 형태로 변경해서 저장해야 하는데 이 과정을
아카이빙
이라고 한다.
- 아카이빙 방법은 struct에 Codable 상속 후, JSONEncoder를 이용해 객체를 아카이빙한다.
- 반대로 메모리, 디스크에 저장된 Data 형태의 바이트를 struct 같은 객체로 바꾸는 것을
언아카이빙
라고 한다.
- 언아카이빙은 JSONDecoder를 사용한다.
- UserDefaults는 Thread-Safe하다. synchronize 메서드를 통해 UserDefaults에 기록된 값을 plist 형식의 파일에 쓰는 작업을 한다. 현재 synchronize 함수를 직접 호출하는 방식은 deprecated 된 상태며, 클래스 deinit시 자동으로 synchronize 메서드가 불린다. 옛날엔 직접 호출했다고 한다!
- forEach와 for-loop의 차이는 forEach는 break가 안 되는데 그렇다고 return을 한다고 해도 끝까지 수행하지만, for-loop는 break를 걸면 멈춘다. 따라서 성능 측면에서 탐색을 끝내도 되는 조건이라면 for-loop를 사용하는 것이 나을 수 있다.
- 해시 테이블에서 충돌이 발생할 경우
open addressing
방식과 separate chaining
방식으로 해결할 수 있다.
- open addressing 방식은 또 세 가지가 있는데 선형탐사, 제곱탐사, 이중해싱 방식이 있다.
- 선형탐사는 충돌이 발생했을 때 해시테이블 인덱스의 탐사 이동폭을 선형적으로 증가시키는 방법이며, 제곱탐사는 인덱스 값의 제곱만큼 증가시키는 방법이다.
- 하지만 선형탐사나 제곱탐사는 탐사 이동폭이 같기 때문에 해시값들이 저장공간 한쪽에 뭉치는
클러스터링
현상이 일어나기에 좋은 탐사방법은 아니다.
- 이중해싱은 클러스터링 문제가 발생하지 않도록 2개의 해시 함수를 사용하는 방식이다.
하나는 해시값을 얻을 때, 다른 하나는 해시 충돌이 발생할 때 탐사 이동폭을 얻기 위해 사용한다.
- separate chaining 방식은 Linked List를 이용한다. 충돌이 발생할 경우 링크드 리스트에 노드(slot)을 추가해서 데이터를 저장한다.
- 삽입과 검색, 삭제의 시간 복잡도는 O(1)이지만, 최악의 경우 O(n)이 될 수 있다.
- 삽입의 경우 서로 다른 두 key가 같은 해시값을 가지면 linked list에 노드를 추가하여 key, value 데이터 쌍을 저장한다.
- 검색은 기본적으로 O(1)의 시간복잡도를 갖지만, O(n)의 시간복잡도를 가질수도 있는데, 이유는 n개의 모든 key가 동일한 해시값을 갖게 되면 길이 n의 선형적인 linked list가 만들어지기 때문이다.
- 삭제를 하기 위해선 검색을 먼저 해야하므로 검색의 시간 복잡도와 동일하다.
내일 일정.
프로그래머스 알고리즘 2문제 이상 풀기
네트워크 꾸준히 복습
자료구조 학습
오늘 느낀 점.
요즘 CS랑 알고리즘 공부하느라 iOS를 좀 오랜만에 봤다.
의존성 관리 라이브러리인 Swinject를 알게됐다. 얼른 플젝에 써보고 싶은데 자꾸 우선순위가 밀린다.ㅠㅠ
면접용은 에버노트에 따로 정리해야겠다.
벌써 TIL의 시퀀스 넘버가 14가 되었다. 140, 1400을 향해 달려가자...
UserDefaults 참고