此代码稍后会因EXC_BAD_ACCESS
而导致崩溃SomeLoader().selectedIndex = 1
class SomeLoader {
// MARK: - Public
var selectedIndex: Int? {
get {
return dataStorage.selectedIndex
}
set {
dataStorage.selectedIndex = newValue
}
}
}
此代码未崩溃:
SomeLoader().selectedIndex = 1
class SomeLoader {
// MARK: - Public
var selectedIndex: Int? {
get {
return dataStorage.selectedIndex
}
set {
dataStorage.updateSelected(index: newValue)
}
}
}
其中:
struct DataStorage<T: Hashable> {
enum Keys: String {
case selectedIndex
}
private func get<U>(forKey key: String) -> U? {
guard let objectData = getData(forKey: key) else {
return nil
}
let object: U? = get(forData: objectData)
return object
}
private func get<U>(forData objectData: Data) -> U? {
return NSKeyedUnarchiver.unarchiveObject(with: objectData) as? U
}
private func save<U>(forKey key: String, object: U) {
let encodedData = NSKeyedArchiver.archivedData(withRootObject: object)
UserDefaults.standard.set(encodedData, forKey: key)
}
}
extension DataStorage {
func updateSelected(index: Int?) {
guard let index = index else {
remove(forKey: Keys.selectedIndex.rawValue)
return
}
saveSelected(index: index)
}
var selectedIndex: Int? {
get {
return get(forKey: Keys.selectedIndex.rawValue)
}
set {
guard let index = newValue else {
remove(forKey: Keys.selectedIndex.rawValue)
return
}
saveSelected(index: index)
}
}
}
为什么呢?这是一个错误吗?
带错误和callstack的屏幕截图。该错误稍后会出现在代码的其他部分。
以下代码在iOS中崩溃。但是在操场上工作。
//: Playground - noun: a place where people can play
import UIKit
struct DataStorage<T: Hashable> {
enum Keys: String {
case selectedIndex
}
private func get<U>(forKey key: String) -> U? {
guard let objectData = getData(forKey: key) else {
return nil
}
let object: U? = get(forData: objectData)
return object
}
private func get<U>(forData objectData: Data) -> U? {
return NSKeyedUnarchiver.unarchiveObject(with: objectData) as? U
}
private func save<U>(forKey key: String, object: U) {
let encodedData = NSKeyedArchiver.archivedData(withRootObject: object)
UserDefaults.standard.set(encodedData, forKey: key)
}
private func remove(forKey key: String) {
UserDefaults.standard.removeObject(forKey: key)
}
private func saveSelected(index: Int) {
save(forKey: Keys.selectedIndex.rawValue, object: index)
}
private func getData(forKey key: String) -> Data? {
return getContent(forKey: key) as? Data
}
private func getContent(forKey key: String) -> Any? {
return UserDefaults.standard.value(forKey: key)
}
}
extension DataStorage {
func updateSelected(index: Int?) {
guard let index = index else {
remove(forKey: Keys.selectedIndex.rawValue)
return
}
saveSelected(index: index)
}
var selectedIndex: Int? {
get {
return get(forKey: Keys.selectedIndex.rawValue)
}
set {
guard let index = newValue else {
remove(forKey: Keys.selectedIndex.rawValue)
return
}
saveSelected(index: index)
}
}
}
class SomeLoader {
// MARK: - Public
var dataStorage = DataStorage<Int>()
var selectedIndex: Int? {
get {
return dataStorage.selectedIndex
}
set {
dataStorage.selectedIndex = newValue
}
}
}
let someLoader = SomeLoader()
someLoader.selectedIndex = 1
print(someLoader)
以下代码无处不在
//: Playground - noun: a place where people can play
import UIKit
struct DataStorage<T: Hashable> {
enum Keys: String {
case selectedIndex
}
private func get<U>(forKey key: String) -> U? {
guard let objectData = getData(forKey: key) else {
return nil
}
let object: U? = get(forData: objectData)
return object
}
private func get<U>(forData objectData: Data) -> U? {
return NSKeyedUnarchiver.unarchiveObject(with: objectData) as? U
}
private func save<U>(forKey key: String, object: U) {
let encodedData = NSKeyedArchiver.archivedData(withRootObject: object)
UserDefaults.standard.set(encodedData, forKey: key)
}
private func remove(forKey key: String) {
UserDefaults.standard.removeObject(forKey: key)
}
private func saveSelected(index: Int) {
save(forKey: Keys.selectedIndex.rawValue, object: index)
}
private func getData(forKey key: String) -> Data? {
return getContent(forKey: key) as? Data
}
private func getContent(forKey key: String) -> Any? {
return UserDefaults.standard.value(forKey: key)
}
}
extension DataStorage {
func updateSelected(index: Int?) {
guard let index = index else {
remove(forKey: Keys.selectedIndex.rawValue)
return
}
saveSelected(index: index)
}
var selectedIndex: Int? {
get {
return get(forKey: Keys.selectedIndex.rawValue)
}
set {
guard let index = newValue else {
remove(forKey: Keys.selectedIndex.rawValue)
return
}
saveSelected(index: index)
}
}
}
class SomeLoader {
// MARK: - Public
var dataStorage = DataStorage<Int>()
var selectedIndex: Int? {
get {
return dataStorage.selectedIndex
}
set {
dataStorage.updateSelected(index: newValue)
}
}
}
let someLoader = SomeLoader()
someLoader.selectedIndex = 1
print(someLoader)