2017-02-09 4 views
1

ich mein Programm debuggen, wenn der Wert einer Eigenschaft zu überprüfen, richtig eingestellt ist, habe ich einen Haltepunkt in dieser Funktion:Was sind Nutzdaten in iOS?

func showContent(data: Any) -> UIView { 
    // breakpoint here 
    var contentView = UIView() 
    if let image = data as? UIImage { 
     let imageView = UIImageView() 
     imageView.image = image 
     contentView = imageView 
    } 
    if let text = data as? String { 
     let label = UILabel() 
     label.centerYAnchor.constraint(equalTo: self.centerYAnchor).isActive = true 
     label.centerXAnchor.constraint(equalTo: self.centerXAnchor).isActive = true 
     label.text = text 
     contentView = label 
    } 
    return contentView 
} 

der an diese Funktion übergebenen Wert von einem View-Controller ist:

override func viewDidLoad() { 
    calcGroupFamiliarity() 
    flashCardView.linkedMemory = Memory(masteryLevel: 1, algorithm: Algorithm.algorithm1.chooseAlgorithm(), forgetRatio: 0, lastStudyTime: Date(), front: #imageLiteral(resourceName: "Ideas-Blue"), back: #imageLiteral(resourceName: "Ideas-Yellow")) 
} 

wie Sie sehen können, sowohl die front und die back sind Bilder jedoch im Debugger sowohl sie als eine payload_data erschienen, während der Datentyp andere Werte wie masteryLevel, algorithm korrekt sind:

enter image description here

Kann jemand erklären, was das bedeutet? Und was soll ich tun, um stattdessen die normalen Bilddaten zu übergeben?

Update:

Dies ist Memory Klasse:

class Memory: NSObject, NSCoding { 

var masteryLevel: Int 
var algorithm: [Int: Double] 
var forgetRatio: Int 
var lastStudyTime: Date 
var strength: Double = 0 
var front: Any 
var back: Any 
static let DocumentsDirectory = FileManager().urls(for: .documentDirectory, in: .userDomainMask)[0] 
static let ArchiveURL = DocumentsDirectory.appendingPathComponent("Memory") 

init(masteryLevel: Int, algorithm: [Int: Double], forgetRatio: Int, lastStudyTime: Date, front: Any, back: Any){ 

    self.masteryLevel = masteryLevel 
    self.algorithm = algorithm 
    self.forgetRatio = forgetRatio 
    self.lastStudyTime = lastStudyTime 
    self.front = front 
    self.back = back 
} 

... 

} 
+0

Für payload_data finden https://medium.com/@ vhart/protocols-generics-and-existential-container-wait-what-e2e698262ab1 # .947l6tczk Wie sieht Ihre Memory-Klasse aus? –

+0

@AndreasOetjen danke, plz siehe das Update –

Antwort

2

Dies ist ein Detail, wie Swift implementiert die Any Typ. Vorausgesetzt, dass Swift nicht im Voraus wissen kann, was Sie z. front, muss ein Zeiger auf das Objekt (in payload_data_0) sowie ein Zeiger auf Metadaten über den Typ des gespeicherten Objekts (in instance_type) gespeichert werden. Soweit ich weiß, sind payload_data_1 und als Optimierung vorhanden, so dass Swift bis zu 24 Byte große Strukturen an Ort und Stelle speichern kann, anstatt sie in ein Wrapper-Objekt zu legen, das in einem separaten Heapspeicherort gespeichert werden muss.

Also, um Ihre Frage zu beantworten: Dies ist weder ein Fehler in Swift, noch ein Fehler auf Ihrer Seite. Ihre Daten werden richtig gespeichert und abgerufen. Wenn Sie es vorziehen würde front leichter beim Debuggen zu überprüfen, versuchen

(lldb) po front 

im Debugger. Alternativ ändern Sie den Typ front in z. UIImage?. Wenn das nicht möglich ist, könnten Sie ein Protokoll

protocol MemoryStoreable: class { } 

erklären und jede Art erweitern, die wie so in diesen Feldern gespeichert werden muss:

extension UIImage: MemoryStoreable { } 

und deklarieren die Variable als

var front: MemoryStoreable? 

Beachten Sie, dass MemoryStoreable auf Klassen beschränkt ist, da andernfalls ein Protokoll-Zeuge gespeichert werden müsste (der wiederum ähnlich wie das Feld , das Sie beobachten, implementiert wird d).

Eine andere Alternative wäre, wenn Sie wissen, dass Sie z.B. nur Bilder und Streicher in front, eine ENUM zu verwenden:

enum MemoryStoreable { 
    case `string`(String) 
    case image(UIImage) 
} 

var front: MemoryStoreable? 

Das noch mindestens 25 Byte Speicherplatz in Ihrem Objekt erfordert (möglicherweise 32 aufgrund Speicherausrichtung constraints), obwohl, wie, dass die Größe der ist String Struktur

Für weitere Einzelheiten siehe z. https://mikeash.com/pyblog/friday-qa-2014-08-01-exploring-swift-memory-layout-part-ii.html.

+0

Das ist eine sehr gute Antwort, dauert eine Weile, um zu verdauen, danke! –

0

Basieren Sie auf @ MrMage's super Antwort.

@MrMage 2 Vorschläge gab, dieses Problem zu nähern, es dauerte einige Anstrengung für mich, sie zu erfassen, für das, was ich in dem Programm erreichen wollte, ist es das perfekte Szenario für mich Protokoll orientiert zu gehen -Programmierung.

Hier ist eine wirklich einfache Anleitung zu verstehen, die mir sehr helfen: Introduction to Protocol Oriented Programming in Swift

Hoffentlich kann dies hilfreich sein :)