使用可编码和静态变量的 Plist 结构类
Posted
技术标签:
【中文标题】使用可编码和静态变量的 Plist 结构类【英文标题】:Plist to struct class with codable and static variables 【发布时间】:2018-01-23 07:44:52 【问题描述】:我有一个 Plist,其中包含端点 URL。我想在应用程序打开后阅读该 Plist 并将其写入我的 URL 结构,并且我想在任何地方访问这些 URL。因此,变量需要是静态的。但是,当我做 var's static 我得到以下错误;
'static var' 声明需要初始化表达式或 getter/setter 说明符。
struct URLs: Codable
static let urlBaseURL: String
static let urlCheckCMS: String
static let urlJSON: String
enum CodingKeys: String, CodingKey
case urlBaseURL = "url_base_url"
case urlCheckCMS = "url_check_cms"
case urlJSON = "url_json"
// MARK: Convenience initializers
extension URLs
init?(data: Data)
guard let me = try? PropertyListDecoder().decode(URLs.self, from: data) else return nil
self = me
init?(_ plist: String, using encoding: String.Encoding = .utf8)
guard let data = plist.data(using: encoding) else return nil
self.init(data: data)
init?(fromURL url: String)
guard let url = URL(string: url) else return nil
guard let data = try? Data(contentsOf: url) else return nil
self.init(data: data)
var plistData: Data?
return try? JSONEncoder().encode(self)
var plist: String?
guard let data = self.plistData else return nil
return String(data: data, encoding: .utf8)
编辑:除了下面的答案,我用下面的代码更改数据初始化类以摆脱可选。使用下面的代码,我检查 plist 并且如果在创建初始化类应用程序时返回 nil 将无法继续工作;
init?(data: Data)
guard let me = try? PropertyListDecoder().decode(URLs.self, from: data) else return nil
self = me
URLs.instance = me
和
static var instance: URLs!
但我仍然不确定这是否是最好的方法。如下文所述;
Loading Configurations from plist into singleton
【问题讨论】:
【参考方案1】:要修复你的编译器错误,你应该为你的静态成员提供一个默认值:
static let urlBaseURL: String = ""
但是,您的代码存在一些主要问题。在可编码结构中使用静态成员不会像您想象的那样工作,因为编码/编码总是在结构的 instances 上运行,而不是在结构类型本身上运行。
您应该从您的变量中删除static
,而是提供一个URLs
的单例实例,然后可以从您应用的所有组件中读取该实例:
struct URLs: Codable
static var instance? = nil
let urlBaseURL: String
let urlCheckCMS: String
let urlJSON: String
在您的启动代码中,您可以设置值:
URLs.instance = URLs(data: yourData)
稍后您可以通过以下方式访问这些值:
let urlBaseURL = URLs.instance?.urlBaseURL
请注意,单例模式经常受到批评,这是有充分理由的;在你的情况下,首先我认为没关系。
【讨论】:
我编辑我的问题。请你再检查一次。谢谢你:) 关于您添加的链接:他们主要讨论您是否应该为您的设置命名和键入访问属性(在您的情况下:urlBaseURL
,urlCheckCMS
,...),或者更确切地说,使用通用的value(forKey:)
样式,调用者负责知道值的名称和类型。在您的情况下,IMO 不是一个问题——您的设置对象中目前只有三个 URL,而 Swift 的 Codable
系统消除了手动保持名称、查找键和类型同步的大部分痛苦。所以我认为你很高兴:)以上是关于使用可编码和静态变量的 Plist 结构类的主要内容,如果未能解决你的问题,请参考以下文章