캡쳐랑 캡쳐리스트 메모리하는날이다
일단 참조타입까지 들어보았다.
메모리 누수 사례까지 해서 객체내의 클로저 사용까지 복습완료. 길었지만 알찼다.
두번들으니 확실히 이해가 더 잘되는 듯 해서 좋다.
가볍게 질문으로 정리
혼동하지 말아야할부분이 몇군데 있는데,
캡쳐타입이 일어나는 경우
캡쳐타입이 값타입에서 일어날때 캡쳐리스트를 안쓰면/쓰면?
캡쳐타입이 참조타입에서 일어날때 캡쳐리스트를 안쓰면/쓰면?
왜 캡쳐타입이 일어나고 왜 캡쳐리스트를 사용하는지?
강한참조 사이클과 강한참조자체(RC를 올리는)는 어떻게 다른지?
weak키워드와 unowned키워드의 공통점과 차이점은 무엇인지? 왜 weak 키워드는 let과 non optional을 쓸수없는지?
무조건 강한참조가 나쁘기만할까? 어떨때 unowned키워드를 사용하고 어떤 효과를 기대할 수 있을까?
ARC : 컴파일러가 retain, release 같은 코드를 자동으로 추가해서 메모리를 관리해줌(안정성 up) 힙영역은 관리필요함
ARC모델 : 소유정책 /참조 카운팅
unowned 참조의 경우 참조하던 인스턴스가 메모리해제가 되어도 nil초기화 없으므로 따로 nil할당 해야함 (에러방지)
값타입의 경우 각 객체의 저장속성에 인스턴스를 할당 => 서로 가르키게 되는 경우 : 강한참조 사이클 => weak, unowned로 해결
캡쳐현상 -값타입 => 외부변수 사용시 함수를 변수에 할당하는 경우 (외부변수의 주소를 캡쳐해서 내 클로저에 저장함) => 캡쳐리스트 사용시 변수 자체의 값을 복사해서 가져옴 (외부 전역변수의 값 변동에 영향안받음)
{[num] in print(num)}
캡쳐현상 -참조타입 => 인스턴스의 주소를 담은 외부 전역변수의 주소를 캡쳐 => 캡쳐리스트 사용시 인스턴스의 주소를 캡쳐 (직접캡쳐 : 강한참조가 되는 셈이다) => 강한참조사이클에 대비해 weak, unowned 와 캡치리스트 조합으로 사용가능 [weak num]
객체내의 클로저 사용시 클로저내에서 객체속성, 매서드를 접근할때 반드시 self 키워드사용 => self.name / [self] in print(name)
구조체는 self 생략가능
객체내 비동기로 클로즈를 실행하는 예시 자주쓰이는 방식 => 강한참조사이클 방지를 위해 weak쓸때 self를 옵셔널 체이닝하여 self?.name과 같이 사용 => 결국 옵셔널 타입이므로(옵셔널체이닝의 결과는 하나라도 옵셔널이면 전체가 업셔널) guard let 바인딩등으로 nil은 제거해주는게 좋음
일부러 강한참조를 사용해서, 인스턴스 생성을 담당한 함수가 종료된 후에도 인스턴스를 클로저로 붙잡음으로써(RC유지) 클로저가 인스턴스 내의 속성을 사용하여 일을 처리할 수 있게끔 할수도 있다. (무조건 나쁜게 x)
오늘도 좋았다.
싱글톤패턴을 구현하는게 어색했다, 앱만들기강의를 들은지 좀 되어서 UIBotton이나 스토리보드 코드구현이 어색해서 아쉬웠다. 반복하면 나아지겠지.
마지막 문제 맞는데 구름 ide에서는 실행이 잘 안되서 시간을 좀 잡아먹었다.
개인적인 포인트 몇개만 TIL에 기록
후행클로저문법 : 파라미터 생략 + 소괄호 생략 (클로저를 쓸때 만큼은)
=> 소괄호가 생략되어있다는것을 절대 잊으면 안됨!(원래 소괄호가 함수의 실행임) => 함수가 실행되고 있다는 걸 잊으면 안됨!
멀티플 후행클로저 문법
파라미터로 함수만 쓰이면 소괄호를 다 생략하고 첫번째 아규먼트 생략가능, 두세번째 아규먼트만 남길 수 있음
=> 원래는 맨 마지막 아규먼트만 생략가능했고 마지막 아규먼트 앞에까지 소괄호 닫는것이었음 (구글검색하면 많이 보이는 코드 읽을 줄 알아야함)