목록swift (51)
develop
반복적으로 메모리를 많이 차지하는 로직을 사용할때 메모리가 해제되지 않고 앱이 죽어버리는 경우가 있다. 메모리를 해제할 시간을 주지않고 계속 메모리를 사용을 해서 생기는 문제이다. 이런 경우에 autoreleasepool을 사용하게 되면 특정 로직을 실행하기 전에 임시오토릴리즈풀이 만들어지고 블럭을 빠져나간 뒤에 임시오토릴리즈풀은 비워지게 되면서 메모리 사용량이 다시 줄어들게 된다. 오토릴리즈풀 블럭 안에서는 return이 되지 않는다. break 는 컴파일에러가 난다. autoreleasepool 함수 안에서 리턴값으로 Result를 받는다. autoreleasepool 함수는 Result를 리턴해준다.
ARC 프로퍼티, 상수, 변수등을 참조하면 레퍼런스가 카운트가 올라가고 참조가 끝나면 레퍼런스 카운터가 내려가고 레퍼런스 카운터가 0이되면 메모리에서 해제한다. 자동 레퍼런트 카운터는 더 이상 사용되지 않는 시점을 결정하여 메모리를 해제한다. 그리고 ARC는 compile time에 코드 분석을 통해 적절한 위치에 retain, release 등의 코드를 삽입해 주고 삽입된 코드는 run time에 실행이 된다 옛날 MRC는 개발자가 직접 리테인과 릴리즈를 해줘야 했고 retain, release를 통해 referenceCount를 증감시키다가 count 가 0이 되면 deinit 을 통해 해제를 하였다. 이러한 작업을 ARC는 자동으로 해준다. 순환참조 메모리가 제대로 해지되지 않는 경우가 있고 순환참..

뷰에 label이 가로로 2개 있다고 가정하고 label의 텍스트가 고정되지 않고 leftLabel은 좌측, 상단에 오토레이아웃이 잡혀있고 rightLabel은 우측, 상단에 오토레이아웃이 잡혀있고 leftLabel의 좌측과 rightLabel의 우측에 오토레이아웃이 연결되어 있다고 가정했을때 let leftLabel = UILabel() leftLabel.translatesAutoresizingMaskIntoConstraints = false view.addSubview(leftLabel) leftLabel.text = "left label" let rightLabel = UILabel() rightLabel.translatesAutoresizingMaskIntoConstraints = false vi..

frame과 bounds의 차이는 1. frame은 x, y가 super 뷰 기준의 좌표계로 설정되고 bounds는 x, y좌표가 자기 자신 기준의 좌표계로 설정된다. let testView = UIView(frame: CGRect(x: 0, y: 100, width: 80, height: 80)) testView.backgroundColor = .blue view.addSubview(testView) print("frame: \(testView.frame)") print("bounds: \(testView.bounds)") frame: (0.0, 100.0, 80.0, 80.0) bounds: (0.0, 0.0, 80.0, 80.0) 2. frame을 변경하게 되면 자기 자신의 좌표가 이동된다. bou..

File - New - Swift Package...를 누른다. 그럼 아래 화면이 나온다. 그리고 라이브러리 명을 입력을 하고 Create를 누른다. 간단하게 SPM 라이브러리가 만들어졌다. Swift파일에 간단하게 소스를 만들어본다. 그리고 git에 프로젝트를 push하고 release를 한다. release를 하지 않으면 다른 프로젝트에서 SPM을 사용할 수 없다. 2021.04.11 - [Library] - Using SPM(Swift Package Manager) 사용하기 Using SPM(Swift Package Manager) 사용하기 File - Swift Packages - Add Package Dependency... 를 선택하면 아래화면이 나온다. SPM을 지원하는 Repository ..

코코아팟 라이브러리 만들기 가이드: guides.cocoapods.org/making/making-a-cocoapod.html CocoaPods Guides CocoaPods is fully open-sourced, so it depends on community contributions to get better. If you're looking to start working on CocoaPods, this is the place to start. guides.cocoapods.org 라이브러리 프로젝트 만들기 터미널에서 pod lib create [라이브러리명] 을 입력을 한다. 플랫폼을 물어보는데 iOS라고 입력을 하고 언어를 물어보는데 Swift라고 입력을 했다. 그리고 데모 앱을 만들건지 물어보..

srt파일이나 smi파일안에 한글이 있다면 아래와 같이 한글이 깨져서 나오게 된다. let urlPath = "https://pikachu987.github.io/ProjectData/Playground/exampleSrt1.srt" guard let url = URL(string: urlPath) else { return } guard let data = try? Data(contentsOf: url) else { return } guard let attributed = try? NSAttributedString(data: data, options: [.documentType: NSAttributedString.DocumentType.html], documentAttributes: nil) else {..
Reorder기능은 셀을 터치한 다음 드래그로 셀의 위치를 바꾸는 기능이다. UITableView Reorder let tableView: UITableView = { let tableView = UITableView() return tableView }() var array: [UIColor] = [.blue, .red, .brown, .black, .green, .gray, .cyan, .orange, .darkGray, .lightGray, .link, .magenta, .purple, .yellow] override func viewDidLoad() { super.viewDidLoad() self.view.addSubview(self.tableView) self.tableView.frame = s..
작업 큐라는 방식이고 병렬프로그래밍을 하기위한 개념이다. 큐에 작업들을 넣으면 알아서 별도의 Thread에서 실행시켜 준다. let queue = OperationQueue() queue.addOperation { (0...3).forEach({ print("queue1: \($0)") }) } let operation = Operation() operation.completionBlock = { () in (0...3).forEach({ print("queue2: \($0)") }) } queue.addOperation(operation) queue1: 0 queue2: 0 queue2: 1 queue1: 1 queue2: 2 queue1: 2 queue2: 3 queue1: 3 간단하게는 Operat..
모든 언어에서 일반적으로 사용되는 병렬프로그래밍 기술인 멀티스레드 하지만 아래의 다른 병렬프로그래밍 기술보다 사용하기가 까다롭고 비효율적이다. Thread에는 Selector을 사용할수 있는 생성자와 block구문을 이용한 생성자가 있다. @available(iOS 2.0, *) public convenience init(target: Any, selector: Selector, object argument: Any?) @available(iOS 10.0, *) public convenience init(block: @escaping () -> Void) Selector을 사용하는 방법이다. override func viewDidLoad() { let thread1 = Thread(target: self..
let workItem = DispatchWorkItem { print("work Item") } workItem.perform() work Item 생성자에 block을 넣는다. perform 메서드로 block를 실행한다. let workItem = DispatchWorkItem { print("work Item") } workItem.notify(queue: DispatchQueue.main) { print("notify") } workItem.perform() work Item notify workItem이 끝나면 notify로 알림을 받을수 있다. let workItem = DispatchWorkItem { print("work Item") } let completeWorkItem = Dispa..
let example = [1,2,3,4,5,6].filter { (value) -> Bool in print("filter: \(value)") return value % 2 == 0 } let example1 = [1,2,3,4,5,6].lazy.filter { (value) -> Bool in print("lazy filter: \(value)") return value % 2 == 0 } filter: 1 filter: 2 filter: 3 filter: 4 filter: 5 filter: 6 lazy를 사용하지 않은 example은 filter가 동작이 된다. lazy를 사용한 example1는 lazy의 뜻에 알맞게 동작이 되지 않는다. let example = [1,2,3,4,5,6].fil..
저장 프로퍼티(Stored Property) struct Example { var value: String } 지연 프로퍼티(Lazy Property) struct Example { lazy var value: String = "" } let example = Example() value에 접근하기 전까지 value는 메모리에 올라가지 않는다. lazy는 let이 될수 없다. let으로 선언된 변수는 초기에 값이 있어야 하는데 lazy는 초기에 값이 존재하지 않고 접근시 값이 생기는 것이라 let을 사용할 수 없다. 만약 변수가 클로저로 되어서 스스로를 참조하면 캡쳐리스트로 메모리 누수를 방지 해야 한다. class Example { var value = "" lazy var closure: () -> ..
KVC는 Key-Value Coding의 약자이다. Swift3에서는 #keyPath()로 키패스를 가져왔지만 Swift4에서는 \만 적어주면 키패스를 가져올수 있게 되었다. class Example: NSObject { var value: String = "" } print(\Example.value) Swift.ReferenceWritableKeyPath 수정도 간단하다. class Example: NSObject { var value: String = "HI" } let example = Example() print(example[keyPath: \Example.value]) example[keyPath: \Example.value] = "HELLO" print(example[keyPath: \Ex..