PFSubclassing с указателем массива и swift 1.2 — фатальная ошибка: элемент NSArray не соответствует типу элемента Swift Array

В Swift 1.2 я больше не могу извлекать массив указателей с подклассом синтаксического анализа и понижать его с помощью другого подкласса синтаксического анализа.

Я всегда находил ошибку:

fatal error: NSArray element failed to match the Swift Array Element type

У вас есть идея или она может прийти?

Код:

import Foundation

class ShotModel : PFObject, PFSubclassing {

    /**
    * MARK: Properties
    */
    @NSManaged var name: String

    @NSManaged var pics: [PicModel]


    override class func initialize() {
        var onceToken : dispatch_once_t = 0;
        dispatch_once(&onceToken) {
            self.registerSubclass()
        }
    }

    class func parseClassName() -> String! {
        return "Shot"
    }

}

import Foundation

class PicModel : PFObject, PFSubclassing {

    /**
    * MARK: Properties
    */
    @NSManaged var name: String


    override class func initialize() {
        var onceToken : dispatch_once_t = 0;
        dispatch_once(&onceToken) {
            self.registerSubclass()
        }
    }

    class func parseClassName() -> String! {
        return "Pic"
    }

}

// this cause error

var shot: ShotModel = // a shot model get with fetchInBackgroundWithBlock

shot.pics // fatal error: NSArray element failed to match the Swift Array Element type

Спасибо за ваше время


person Antoine Lenoir    schedule 13.03.2015    source источник
comment
Примените shot к PFObject вместо ShotModel, тогда вы можете получить shot.valueForKey("pics"). Попробуйте, раз у меня получилось.   -  person Rahul Mane    schedule 13.03.2015
comment
Да, у меня есть доступ к shot.valueForKey("pics") с приведением ShotModel, но я не могу преобразовать shot.valueForKey("pics") в [PicModel]   -  person Antoine Lenoir    schedule 13.03.2015
comment
Попробуйте изменить @NSManaged var pics: [PicModel] на ` @NSManaged var pics: [PFObject]` У меня была такая же проблема, решенная путем приведения к PFObject   -  person Rahul Mane    schedule 13.03.2015
comment
хорошо, но как получить массив объектов PicModel? Я пытался, но у меня есть другая ошибка, когда я делаю это: pis as! PicModel => Could not cast value of type 'PFObject' to 'PicModel' ...   -  person Antoine Lenoir    schedule 13.03.2015
comment
Нашел похожий пост на Github — github.com/burczyk/ParseCollectionsSwiftBug. Может быть, это могло бы помочь вам.   -  person Rahul Mane    schedule 13.03.2015


Ответы (4)


Проблема исходит из этой части кода:

override class func initialize() {
    var onceToken : dispatch_once_t = 0;
    dispatch_once(&onceToken) {
        self.registerSubclass()
    }
}

registerSubclass() для ShotModel вызывается перед registerSubclass() для PicModel.

Я решил это в AppDelegate :

PicModel.registerSubclass()
ShotModel.registerSubclass()
person Antoine Lenoir    schedule 13.03.2015
comment
Это не работало для меня, пока я не поставил вызовы .registerSubclass() перед инициализацией Parse. Теперь он отлично работает. Разочаровывающий баг однако. Спасибо! - person Rick Roberts; 29.04.2015
comment
Я решил это, добавив PicModel.initialize() в первую строку инициализации ShotModel. - person zirinisp; 06.05.2015
comment
На самом деле я зарегистрировал ошибку (developers.facebook.com/bugs/1452388645073907) в разборе этого по той же причине, и в итоге они обновили свою документацию следующим образом: обратите внимание, что метод инициализации не вызывается до тех пор, пока класс не получит свое первое сообщение, а это означает, что вам нужно вызвать любой экземпляр или метод класса в вашем подклассе, прежде чем он будет зарегистрирован с Parse SDK.` - person Julian B.; 28.05.2015
comment
Спасибо. это определенно помогло. - person RyanPliske; 27.09.2015

Проблема заключается в том, что ShotModel зарегистрирован как подкласс перед PicModel. Чтобы инвертировать это, мы можем назвать инициализацию PicModel инициализацией ShotModel.

Таким образом, мы сохраняем предложенное решение путем синтаксического анализа и следим за тем, чтобы классы регистрировались в правильном порядке.

class ShotModel : PFObject, PFSubclassing {

    /**
    * MARK: Properties
    */
    @NSManaged var name: String

    @NSManaged var pics: [PicModel]


    override class func initialize() {
        var onceToken : dispatch_once_t = 0;
        dispatch_once(&onceToken) {
            PicModel.initialize()
            self.registerSubclass()
        }
    }
person zirinisp    schedule 06.05.2015
comment
Это было очень полезно. Спасибо - person E-Madd; 30.09.2015

Каким-то образом мне пришлось также инициализировать объект после регистрации в AppDelegate:

PicModel.registerSubclass()
PicModel()
ShotModel.registerSubclass()
ShotModel()
person Aviel Gross    schedule 09.04.2015

На самом деле я отправил ошибку синтаксического анализа по той же самой причине, и в итоге они обновили свой подклассы со следующим:

Please note that the initialize method is not called until the class receives its first message, meaning that you need to call any instance or class method on your subclass before it will be registered with Parse SDK.

Таким образом, вам НЕОБХОДИМО вызвать метод registerSubclass() или любой другой метод для правильной регистрации класса в Parse.

person Julian B.    schedule 28.05.2015