web-dev-qa-db-ja.com

格納されているすべてのプロパティを初期化せずに初期化子から戻る

このような単純なクラスがあります。

public class User {
    let id: Int
    let firstName: String
    let lastName: String
    let email: String?

    init(id: Int, firstName: String, lastName: String) {
        self.id = id
        self.firstName = firstName
        self.lastName = lastName
    }
}

これは以前のSwiftバージョンで正常にコンパイルされました。Swift 1.2では、次のコンパイルエラーが発生します。

保存されているすべてのプロパティを初期化せずに初期化子から戻る

なぜですか、どうすれば解決できますか?

34
Isuru

プロパティが定数であるため、letを使用して作成された場合、initであっても、その場所またはOptionalメソッドで初期化する必要があります。オプションでメールを設定できるようにするには、letvarに変更する必要があります。つまり、initメソッドまたはクラス本体で変数を初期化していない場合、変数はvarOptionalの両方である必要があります。

docs の関連ステートメント:

初期化が終了するまでに特定の値に設定されている限り、初期化中の任意の時点で値を定数プロパティに割り当てることができます。定数プロパティに値が割り当てられると、それ以上変更することはできません。

クラスインスタンスの場合、定数プロパティは、それを導入するクラスによる初期化中にのみ変更できます。サブクラスでは変更できません。

53
Dániel Nagy

経験則は次のとおりです。

  • Letを使用している場合は、それを初期化する必要があります(オプションであっても)。例:let email: String
  • non optional varがある場合は、初期化する必要があります。例:var email: String
  • オプションの変数がある場合は、初期化する必要はありません。例:var email: String?
23
Tiago Almeida

電子メールの値は定数であるため、明示的に設定する必要があります。

public class User {
    let id: Int
    let firstName: String
    let lastName: String
    let email: String?

    init(id: Int, firstName: String, lastName: String) {
        self.id = id
        self.firstName = firstName
        self.lastName = lastName
        self.email = nil // <--------------
    }
}

または、他の人が述べたように、電子メールを変数に変更できます。

17
Onato

以下のように、メールを「let」から「var」に変更します。

public class User {
    let id: Int
    let firstName: String
    let lastName: String
    var email: String?

    init(id: Int, firstName: String, lastName: String) {
        self.id = id
        self.firstName = firstName
        self.lastName = lastName

    }
}
6
Chamath Jeevan

まず、すべてのlet変数に宣言時に値を割り当てる必要があることを明確にします。だからあなたの声明は

let id: Int  = 0
let firstName: String = "test"
let lastName: String = "Test"
let email: String? = "Test"

次に、クラスでは、変数を初期化するか、「?」を入力してオプションの型として定義する必要がありますまたは「!」すべての変数で。いいね

let id: Int!
let firstName: String!
let lastName: String!
let email: String?

または

let id: Int?
let firstName: String?
let lastName: String?
let email: String?

しかし、これらの変数は定数であるため変更できないことをここで言いたいと思います。そのため、宣言時に値を渡さない場合は、これらと一緒にvarを使用する必要があります。この場合の最終的なコードは、このようなものになります

var id: Int
var firstName: String
var lastName: String
var email: String?
4
Saad