Carl Hung
Carl Hung

Reputation: 555

using initializer in enum and assign to self

my code:

enum Grade: String{
    case A, B, C, D, E, F, U, S
    init!(_ result: Int){
        if result > 100 {
            return nil
        }
        switch result {
        case 0:
            self = .U
        case 1...49:
            self = .F
        case 0:
            self = .U
        case 50...59:
            self = .E
        case 60...69:
            self = .D
        case 70...79:
            self = .C
        case 80...89:
            self = .B
        case 90...99:
            self = .A
        case 100:
            self = .S
        default:
            break
        }
    }
}

It looks alright, but i got error.

error: 'self' used before all stored properties are initialized.

my way to fix it is assign something to self in initializer then using switch.

I want to know if there are better solutions?

thanks.

Upvotes: 2

Views: 1224

Answers (2)

Code Different
Code Different

Reputation: 93191

The error was because you didn't specify a return value in the default statement. Also yours is an init! which make no sense to me.

Try this:

enum Grade: String {
    case A, B, C, D, E, F, U, S

    init?(_ result: Int){
        guard 0...100 ~= result else {
            return nil
        }

        switch result {
        case 0:
            self = .U
        case 1...49:
            self = .F
        case 50...59:
            self = .E
        case 60...69:
            self = .D
        case 70...79:
            self = .C
        case 80...89:
            self = .B
        case 90...99:
            self = .A
        case 100:
            self = .S
        default:
            return nil
        }
    }
}

You can make it non-nullable by treating scores below 0 as 0 and above 100 as 100:

enum Grade: String {
    case A, B, C, D, E, F, U, S

    init (_ result: Int) {
        switch result {
        case Int.min...0:
            self = .U
        case 1...49:
            self = .F
        case 50...59:
            self = .E
        case 60...69:
            self = .D
        case 70...79:
            self = .C
        case 80...89:
            self = .B
        case 90...99:
            self = .A
        case 100..<Int.max: // 100...Int.max is a bug in Swift 2, fixed in Swift 3
            self = .S
        default:
            self = .U // Even though all the cases above are exhaustive, the compiler
                      // does not know that. Hence, we still need a default, but it
                      // will never be reached
        }
    }
}

Upvotes: 0

Kristijan Delivuk
Kristijan Delivuk

Reputation: 1252

You get that error because you didn't define self in "default" case.

To remove the error define like one more case (for example .None) and put it in "default". Or you can create failable initializer (init?) and then define self as nil in default case.

Upvotes: 2

Related Questions