• 사진 세트와 같은 정렬된 콘텐츠 세트를 관리하고 커스텀 가능하고 시각적인 레이아웃으로 제공
  • 컬렉션은 엄격하게 선형 형식을 시행하지 않기 때문에 크기가 다른 항목을 표시하는 데 적합
  • 컬렉션은 이미지 기반 콘텐츠를 과시하는 데 이상적
  • 배경과 같은 부수적인 뷰는 항목의 하위 집합을 시각적으로 구별하기 위해 선택적으로 구현
  • 컬렉션은 상호 작용과 애니메이션을 모두 지원한다
  • 기본적으로 탭하여 선택하고, 길게 터치하여 편집하고, 스와이프하여 스크롤할 수 있다
  • 필요한 경우, 커스텀된 작업을 수행하기 위해 더 많은 제스처를 추가할 수 있다
  • 컬렉션 내에서 항목을 삽입, 삭제 또는 재정렬할 때마다 애니메이션을 활성화할 수 있으며 커스텀 애니메이션도 지원한다

 

고려사항

  • 행이나 그리드 레이아웃이 충분할 때 새로운 디자인을 만들지 마세요.
    • 컬렉션은 사용자 경험을 향상시켜야 합니다.
    • 항목을 쉽게 선택할 수 있도록 하세요. 컬렉션에서 항목을 탭하는 것이 어렵다면, 유저입장에서 앱에대한 불편한 인식을 남길수 있습니다.
    • 레이아웃을 깨끗하게 유지하고 콘텐츠가 겹치지 않도록 콘텐츠 주위에 적절한 패딩을 사용하세요.
  • 컬렉션에 텍스트만 표시한다면, 테이블 뷰를 고려하세요.
    • 스크롤 가능한 목록에 표시될 때 텍스트 정보를 테이블 뷰로 구성하는 것이 더 간단하고 효율적입니다.
  • 동적 레이아웃을 변경할 때 주의하세요.
    • 컬렉션의 레이아웃은 언제든지 변경할 수 있습니다.
    • 사람들이 레이아웃을 보고 상호 작용하는 동안 레이아웃을 동적으로 변경한다면, 변경 사항이 합리적이고 추적하기 쉬운지 확인하십시오.
    • 동기 부여되지 않은 레이아웃 변경은 앱을 예측할 수 없고 사용하기 어렵게 만들 수 있습니다.
    • 레이아웃 변경으로 인해 컨텍스트가 손실되면, 유저 입장에서 불편한 앱으로 인식될 수 있습니다.

 참고 문서

TableView를 기준으로 설명 , (아마도) 동일한 프로토콜이 있다면 같은 기능을 수행할 것입니다.

Delegate

  • TableCell을 탭(클릭) 했을때 어떠한 기능을 수행하는 권한을 위임하는 프로토콜
func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: IndexPath) 
func tableView(tableView: UITableView, willBeginEditingRowAtIndexPath indexPath: IndexPath)
  • 외울필요? X 자동완성을 사용하자 ( 우리 신세대임..ㅋ )
  • 메서드의 인자만 봐도 어떤 기능을 수행 할 지 짐작이 가능하다
  • didSelectRowAtIndexPath → 이름부터가 선택 됐을때, 어떠한 동작을 수행할 것인지 에 대한 정의를 내리면 될것 같다
  • willBeginEditingRowAtIndexPath ⇒ 공식문서 의 내용을 보니 행의 삭제와 같은 기능을 수행 할 때 어떤 동작을 결정할 지를 정의하면 된다

⇒ 물론 Delegate의 func들은 Optional이기 때문에 반드시 정의 할 필요는 없다.

 

DataSource

  • TableView의 Cell을 어떻게 보여줄가 에 대한 권한을 위임(?) 하는 프로토콜
  • 몇개의 행을 표시할 것인지? 각 행에는 어떤 내용을 보여줄 것인지등등 간단히 말해 View를 그리는 역할을 수행한다고 생각하면 된다
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: IndexPath) -> UITableViewCell
func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int
  • 위 두가지 메서드는 Datasource 프로토콜을 채택 할 때 반드시 정의해 줘야 하는 메서드!
  • 외우지 말자.. ( Datasource 채택하면 빨간줄 뜨면서 자동으로 채워진다! )
  • numberOfRowsInSection ⇒ 이름만 봐도 몇개의 섹션을 나눌것 인지 정의하면 된다. 말 그대로 몇개의 행을 테이블 뷰에 표시 해 줄것인지 정의해 주면 된다 ( 정수를 반환하면 반환된 값 만큼 테이블뷰의 행이 생성된다 )
  • cellForRowAtIndexPath ⇒ 각 행(cell)에 어떤 내용을 보여 줄 것인지 정의해 주면 된다. 말 그대로 어떤 내용을 표시해 줄지에 대한 정의를 내리면 되고, indecPath 를 통해 각 행이 for 구문 처럼 순차적으로 정의된다 ( 이해가 안가면 직접 구현해 보자 )
  • 두개의 메서드 말고 추가적인 메서드들도 있으나, 모두 외울 필요없다, 필요하면 그때 그때 찾아 사용하자

⇒ 한줄 정리 : Delegate는 어떠한 동작 을 수행, DataSource는 어떠한 내용 을 표시

문제

 

풀이 코드

let inputs = readLine()!
var stack = ""
var answer = ""

for op in inputs {
    switch op {
    case "(":
        stack.append(op)
    case ")":
        while !stack.isEmpty && stack.last != "("{
            answer.append(stack.removeLast())
        }
        stack.removeLast()
    case "*", "/":
        while !stack.isEmpty && (stack.last == "*" || stack.last == "/") {
            answer.append(stack.removeLast())
        }
        stack.append(op)
    case "+", "-":
        while !stack.isEmpty && stack.last != "(" {
            answer.append(stack.removeLast())
        }
        stack.append(op)
    default:
        answer.append(op)
    }
}

while !stack.isEmpty {
    answer.append(stack.removeLast())
}
print(answer)

 

풀이 과정

스택을 이용하여 풀이 하였다.

괄호를 만나면 일단 스택에 넣어주고, 닫는 괄호가 나왔을때, 우선순위가 모두 종료된 의미이기 때문에 스택에 있는 연산자를 모두 꺼내 주었고,

곱셈 이나 나눗셈을 만나면 곱셈 나눗셈까지 모두 꺼내 주고, 

덧셈이나 뺄셈이 나오면 괄호 를 만날때 까지 꺼내주었다.

문제

 

풀이 코드

import Foundation

let N = Int(readLine()!)!
let formula = readLine()!
var num = [Int]()
var answer = [Double]()

for _ in 0..<N {
    num.append(Int(readLine()!)!)
}

for op in formula {
    switch op {
    case "*":
        answer.append(answer.removeLast() * answer.removeLast())
    case "/":
        let stackLast = answer.removeLast()
        answer.append(answer.removeLast() / stackLast)
    case "+":
        answer.append(answer.removeLast() + answer.removeLast())
    case "-":
        let stackLast = answer.removeLast()
        answer.append(answer.removeLast() - stackLast)
    default:
        let idx = op.asciiValue! - 65
        answer.append(Double(num[Int(idx)]))
    }
}

print(String(format: "%.2f", answer.removeLast()))

 

풀이 과정

알파벳을 포함한 별도의 배열을 선언해 주고 계산을 해야하나 고민했는데,

Ascii 코드를 이용해서 인덱스를 할당하여 구현하면 된다고 생각했다.

 

A 의 아스키 코드는 65 이고, 입력받은 숫자들을 별도의 배열로 지정하여

A 일때는 0인덱스의 수를, B일때는 1인덱스의 수를 ... 이렇게 할당하면 될것같았다.

 

그렇게 그냥 스택을 이용해 풀이를 해주었고, 고려해야 할 점은 두가지였다.

- 와 / 인데,

 

덧셈과 곱셈의 경우 순서가 상관 없지만, 뺄셈과 나눗셈은 순서가 중요하기 때문에, 먼저 removeLast 를 수행하여 순서를 지정해 주었다.

 

이렇게 풀고 소숫점 2번째 자리까지만 출력하기 위해

String의 format 을 이용해 C언어의 printf 처럼 할당해 주었다

문제

 

풀이 코드

let N = Int(readLine()!)!
var nums = readLine()!.split(separator: " ").map{Int(String($0))!}
var numCount = Array(repeating: 0, count: nums.max()!)
var answer = [Int]()

// 등장횟수 계산
for idx in 0..<N {
    numCount[nums[idx] - 1] += 1
}

// 오등큰수 인덱스 검색
for idx in 0..<N {
    while !answer.isEmpty && numCount[nums[answer.last!] - 1] < numCount[nums[idx] - 1] {
        nums[answer.removeLast()] = nums[idx]
    }
    answer.append(idx)
}

for idx in answer {
    nums[idx] = -1
}

print(nums.map{String($0)}.joined(separator: " "))

 

풀이 과정

이전에 풀었던 오큰수와 크게 다르지 않은 문제라서 거의 코드를 가져온 수준이였다.

대신 다른점이 있다면, 입력된 값 내에서 최대값만큼 배열을 생성해 주었고, count 를 계산하여

count 를 비교하며 오큰수와 같은 형식으로 풀었다.

+ Recent posts