ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • swift - Enumerations(RawValue, Associated Value, Enumeration case Pattern)
    swift 2021. 1. 7. 19:18

    Enumerations(열거형)

    // 열거형
    // 열거형에 포함된 상수들은 상수라고 부르지 않고 Enumeration case 혹은 case로 부름
    // 코드의 가독성, 안정성 향상
    
    // 열거형을 사용하지 않았을때 발생하는 오류
    
    //let left = 0
    //let center = 1
    //let right = 2
    //
    //var aligment = center
    
    
    // 규칙을 모르더라도 값만으로 어떤 의미인지 파악할 수 있게
    
    // 가독성은 증가했지만 문자열이기 때문에 오타가 발생할 수도 있고 비교 기준을 명확히해야함(대소문자 등)
    let left = "left"
    let center = "center"
    let right = "right"
    
    var aligment = center
    
    // 대문자라서 false
    if aligment == "Center" {
        
    }
    

    // 열거형 case는 독립적인 값
    enum Alignment {
        case left
        case right
        case center
    }
    
    Alignment.center
    
    var textAlignment = Alignment.center
    print(textAlignment)
    
    // 앞에서 열거형을 작성했기 때문에 어떤 열거형인지 추론할 수 있기 때문에 .left만 적어줘도 된다.
    textAlignment = .left
    
    // enum case는 값이기 때문에 == 으로 구분한다.
    if textAlignment == .center {
        
    }
    
    //switch
    switch textAlignment {
    case .left:
        print("left")
    case .right:
        print("right")
    case .center:
        print("center")
    }

    Raw Values

    // 원시값
    // case와 함께 다른 값을 선언해야 할때 사용
    
    enum Alignment: Int {
        //  Int가 raw Value이고 값을 지정해주지 left부터 순서대로 0 1 2
        case left
        case right
        case center
        case leftInt = 5
        case rightInt  // 요곤 그전 값 +1
    }
    
    Alignment.leftInt.rawValue
    Alignment.left.rawValue
    Alignment.rightInt.rawValue
    
    // rawValue에 새로운 값 넣는거 불가능
    // Alignment.right.rawValue = 5
    
    // rawValue에 해당하는 case 리턴됨
    Alignment(rawValue: 5)
    
    // rawValue에 해당하는 값 없으면 nil
    Alignment(rawValue: 200)
    
    
    
    enum Weekday: String {
        case sunday
        case monday = "MON"
        case tuesday
        case wednesday
        case thursday
        case friday
        case saturday
    }
    // rawValue가 String이면 case에 해당하는 String리턴
    Weekday.sunday.rawValue
    
    // 값이 있으면 지정한 값 리턴
    Weekday.monday.rawValue
    
    
    // rawValue를 Character로 선언한 경우에는 반드시 rawValue를 직접 지정해야 한다.
    enum ControlChar: Character {
        case tab = "\t"
        case newLine = "\n"
    }

    Associated Value

    // enum case에 연관된 값을 저장한다.
    enum VideoInterface: String {
        case dvi = "1028x768"
        case hdmi = "2048x1536"
        case displayPort = "3840x2160"
    }
    
    // 이렇게하면 문자를 숫자로 추출해야한다.
    // 이렇게 원시값으로 해상도를 저장하면 전부 공유
    
    
    
    // associated Values
    // 1. 저장할 자료형을 개별 case별로 가능
    // 2. () 튜플로 선언
    // 3. case뒤에 선언
    // 4. 선언할 수 있는 형식에 제한이 없음
    // 5. 하나의 케이스에서 서로 다른 자료형을 선언할 수 있음
    
    enum AssociatedVideoInterface {
        // named Tuple로 선언가능
        case dvi(width: Int, height: Int)
        // Unnamed Tuple로도 선언가능
        case hdmi(Int, Int, Double, Bool)
        case displayPort(CGSize)
    }
    
    var input = AssociatedVideoInterface.dvi(width: 2048, height: 1536)
    
    // 연관값을 코드로 확인할 때는 주로 switch문을 사용
    // enumeration case parttern
    switch input {
    case .dvi(width: 2048, height: 1536):
        print("dvi 2048 x 1536")
    case .dvi(2048, _): // 와일드 카드 패턴으로 높이를 생략
        print("div 2048 x Any")
    case .dvi: // 연관값 무시하고 case만 일치시킬 때
        print("dvi")
    case .hdmi(let width, let height, let version, let audioEnabled): // 연관값을 상수로 바인딩
        print("hdmi \(width)x\(height)")
    case let .displayPort(size): // 모든 연관 값을 동일한 case로 바인딩 하는 경우
        print("dp")
    
    }
    
    input = .hdmi(3080, 2160, 2.1, true)
    input

    Enumberation Pattern

    // Enumeration Case Pattern
    // 연관값을 가진 열거형 case를 매칭시킬때 사용
    // switch, if, guard, for-in문에서 사용
    
    enum TransPortation {
        case bus(number: Int)
        case taxi(company: String, number: Int)
        case subway(lineNumber: Int, express: Bool)
    }
    
    var tpt = TransPortation.bus(number: 7)
    
    // swich문에서 enumeration case pattern
    switch tpt {
    case .bus(let n): // bus case를 매칭시키고 연관값은 n 상수에 바인딩
        print(n)
    case .taxi(let c, var n):
        print(c, n)
    case let .subway(l, e):
        print(l, e)
    }
    
    tpt = TransPortation.subway(lineNumber: 2, express: false)
    
    // if문에서 enumeration case pattern
    if case let .subway(2, express) = tpt { // .subway의 lineNumber가 2 일때 true
        if express {
            
        } else {
            
        }
    }
    
    // 지금은 값을 바인딩하지 않아서 case 뒤에 let 이나 var 키워드를 쓰지 않음
    if case .subway(_, true) = tpt {
        print("express")
    }
    
    let list = [
        TransPortation.subway(lineNumber: 2, express: false),
        TransPortation.bus(number: 4412),
        TransPortation.subway(lineNumber: 7, express: true),
        TransPortation.taxi(company: "SeoulTaxi", number: 1234)
    ]
    
    for case let .subway(n, _) in list {
        print("subway \(n)")
    }
    
    for case let .subway(n, true) in list {
        print("subway \(n)")
    }
    
    for case let .subway(n, true) in list where n == 2 {
        print("subway \(n)")
    }

    댓글

Designed by Tistory.