Klasa nie ma inicjatorów Swift

181

Mam problem z klasą Swift. Mam szybki plik dla klas UITableViewController i UITableViewCell. Moim problemem jest klasa UITableViewCell i gniazda. Ta klasa ma błąd Klasa „HomeCell” nie ma inicjatorów i nie rozumiem tego problemu.

Dziękuję za twoje odpowiedzi.

import Foundation
import UIKit

class HomeTable: UITableViewController, UITableViewDataSource, UITableViewDelegate {

    @IBOutlet var tableViex: UITableView!

    var items: [(String, String, String)] = [
        ("Test", "123", "1.jpeg"),
        ("Test2", "236", "2.jpeg"),
        ("Test3", "678", "3.jpeg")
    ]

    override func viewDidLoad() {
        super.viewDidLoad()

        var nib = UINib(nibName: "HomeCell", bundle: nil)
        tableView.registerNib(nib, forCellReuseIdentifier: "bookCell")
    }

    // Number row
    override func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return self.items.count
    }

    // Style Cell
    override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {

        var cell:UITableViewCell = self.tableView.dequeueReusableCellWithIdentifier("bookCell") as UITableViewCell

        // Style here

        return cell

    }

    // Select row
    override func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {
        // Select
    }

}

// PROBLEM HERE
class HomeCell : UITableViewCell {

    @IBOutlet var imgBook: UIImageView
    @IBOutlet var titleBook: UILabel
    @IBOutlet var pageBook: UILabel

    func loadItem(#title: String, page: String, image:String) {
        titleBook.text = title
        pageBook.text = page
        imgBook.image = UIImage(named: image)
    }

}
Kevin Py
źródło
Czy musisz jawnie podać typ zmiennej stalówki jako opcjonalny UINib?
Cocoadelica,

Odpowiedzi:

257

Musisz użyć niejawnie nieopakowanych opcji, aby Swift mógł poradzić sobie z zależnościami kołowymi (w tym przypadku nadrzędnym <-> potomkiem składników interfejsu użytkownika) podczas fazy inicjalizacji.

@IBOutlet var imgBook: UIImageView!
@IBOutlet var titleBook: UILabel!
@IBOutlet var pageBook: UILabel!

Przeczytaj ten dokument , wszystko ładnie wyjaśnią.

mprivat
źródło
21
Twoje wyjaśnienie i ten dokument mają dla mnie sens, ale nie komunikat o błędzie!
coco
4
To prawdopodobnie pytanie do Apple
mprivat
Również @IBOutlety należy oznaczyć jako słabe, aby uniknąć zatrzymania cyklu.
Dennis Pashkov
@Dennis Pashkov O ile mi wiadomo, to tylko dla IBOutletów, które są w widoku viewController hierarchii. W przeciwnym razie zostanie natychmiast zwolniony, ponieważ nikt go nie trzyma.
Alston
3
Miałem ten problem, gdy zdefiniowałem użycie Boola var myBool: Bool.
Jungledev
96

Szybka poprawka - upewnij się, że wszystkie zmienne, które nie zostaną zainicjowane podczas ich tworzenia (np. var num : Int?Vs var num = 5), mają albo a ?lub !.

Długa odpowiedź (zalecane) - przeczytaj dokument zgodnie z sugestią mprivat ...

Byron Coetsee
źródło
Aby rozwiązać ten błąd, musisz ustawić wartość domyślną dla? zmienne, na przykład: let showUserPointViewDelegate: ShowUserPointsViewControllerControl? = zero
Vladimir Vodolazkiy
+1 ?oznacza, że ​​może być zero, ale jeśli tak, to nie ma problemu z przejściem do przodu i nic nie robieniem.!oznacza, że ​​jeśli po rozpakowaniu było zero, to awaria - oba spełniają wymóg inicjacji - informując kompilator: Wiem / chcę, aby zaczął się od zera.
Honey,
Szukać vari letna wyświetlanie kontrolera i szukać brakujących !s i ?s
Wiingaard
33

To jest z dokumentu Apple

Do czasu utworzenia instancji tej klasy lub struktury wszystkie klasy i struktury muszą ustawić wszystkie swoje przechowywane właściwości na odpowiednią wartość początkową. Zapisanych właściwości nie można pozostawić w nieokreślonym stanie.

Pojawia się komunikat o błędzie Klasa „HomeCell” nie ma inicjatorów, ponieważ zmienne są w nieokreślonym stanie. Albo tworzysz inicjalizatory, albo czynisz je opcjonalnymi typami, używając! czy?

CodeHelp
źródło
32

Moja odpowiedź dotyczy błędu w ogóle, a nie dokładnego kodu PO. Żadna odpowiedź nie wspomniała o tej notatce, więc pomyślałem, że ją dodam.

Poniższy kod również wygeneruje ten sam błąd:

class Actor {
    let agent : String? // BAD! // Its value is set to nil, and will always be nil and that's stupid so Xcode is saying not-accepted.  
    // Technically speaking you have a way around it🤓, you can help the compiler and enforce your value as a constant. See Option3
}

Inni wspominali, że albo tworzysz inicjatory, albo tworzysz z nich opcjonalne typy, używając! czy? który jest poprawny. Jeśli jednak masz opcjonalny element członkowski / właściwość, ten opcjonalny powinien być modyfikowalny, tj var. Jeśli zrobisz, letto nigdy nie będzie będzie w stanie wyjść z tego nilstanu. To źle!

Prawidłowy sposób pisania to:

Opcja 1

class Actor {
    var agent : String? // It's defaulted to `nil`, but also has a chance so it later can be set to something different || GOOD!
}

Lub możesz napisać to jako:

Opcja 2

class Actor {
let agent : String? // It's value isn't set to nil, but has an initializer || GOOD!

init (agent: String?){
    self.agent = agent // it has a chance so its value can be set!
    }
}

lub domyślnie przyjmuje dowolną wartość (w tym nil trochę głupią)

Opcja 3

class Actor {
let agent : String? = nil // very useless, but doable.
let company: String? = "Universal" 
}

Jeśli jesteś ciekawy, dlaczego let(w przeciwieństwie do var) nie został zainicjowany, nilprzeczytaj tutaj i tutaj

kochanie
źródło
2
Dziękujemy za dodanie tego, ponieważ była to krytyczna część obrazu.
Jim
Dobrze wyjaśnione !!
Mahendra
1
Ustawienie na zero nie jest głupie, ale nieodłączne od tego, ile modeli działa.
zremisował ..
@ drew .. ustawienie czegoś niezmiennego niljest bardzo złe. Ustawianie varTO niljest inna sprawa.
Honey
hej Kochanie, kto mówił do niezmiennych przedmiotów?
zremisował ..
10

W moim przypadku zadeklarowałem coś Booltakiego:

var isActivityOpen: Bool 

tzn. zadeklarowałem to bez rozpakowywania, więc oto jak rozwiązałem błąd ( brak inicjatora ):

var isActivityOpen: Bool!
Anurag Sharma
źródło
1

Nie jest to konkretna odpowiedź na twoje pytanie, ale dostałem ten błąd, gdy nie ustawiłem wartości początkowej dla wyliczenia, deklarując go jako właściwość. Przypisałem wartość początkową do wyliczenia, aby rozwiązać ten błąd. Publikowanie tutaj, ponieważ może to komuś pomóc.

Sonu VR
źródło
0

po prostu podaj blok inicjujący dla klasy HomeCell

w moim przypadku to praca

anoopbryan2
źródło