Generics 如何使用NSKeyedArchiver实现在Swift中保存不同词典的通用方法?
抱歉,如果这是一个简单的问题,但我三天都找不到答案。我刚接触斯威夫特 问题:我想使用Swift枚举类型作为不同Swift字典的键,并使用NSKeydArchiver以通用方式保存这些字典 首先,我展示了一些简单的enum和dictionary示例代码(我知道,我可以将dictionary值作为rawValues直接集成到enum声明中,但这不是我的问题,我的问题是使用NSKeydArchiver->参见下面的函数保存dictionary)Generics 如何使用NSKeyedArchiver实现在Swift中保存不同词典的通用方法?,generics,dictionary,swift,nskeyedarchiver,Generics,Dictionary,Swift,Nskeyedarchiver,抱歉,如果这是一个简单的问题,但我三天都找不到答案。我刚接触斯威夫特 问题:我想使用Swift枚举类型作为不同Swift字典的键,并使用NSKeydArchiver以通用方式保存这些字典 首先,我展示了一些简单的enum和dictionary示例代码(我知道,我可以将dictionary值作为rawValues直接集成到enum声明中,但这不是我的问题,我的问题是使用NSKeydArchiver->参见下面的函数保存dictionary) //--------------------------
//------------------------------------------------------
//枚举和字典
// ------------------------------------------------------
枚举Helloopions{
案例选择1
案例选择2
案例选择3
}
枚举某人枚举{
果岭
壳红
箱蓝
}
var myDictionary01:Dictionary=[helloOptions.option1:“你好”,helloOptions.option2:“欢迎”,helloOptions.option3:“很高兴见到你”]
var myDictionary02:Dictionary=[someOtherEnum.green:22,someOtherEnum.red:11,someOtherEnum.blue:999]
这是我对savingFunction的工作实现,但不幸的是,这不是一种通用的方法,因为我需要为应用程序中的所有枚举多次实现此函数
func saveDictionary(myDictionary: Dictionary<helloOptions, AnyObject>, myFileName: String, myDataFolder: DataFolder) -> Bool {
let completeDataPath = makeCompletePathToFile(myFileName, myDataFolder)
let saveSuccess : Bool = NSKeyedArchiver.archiveRootObject(myDictionary, toFile: completeDataPath)
if !saveSuccess {
println("Some problem saving Dictionary")
}
return saveSuccess
}
func保存字典(myDictionary:Dictionary,myFileName:String,myDataFolder:DataFolder)->Bool{
让completeDataPath=makecompletedpathtofile(myFileName,myDataFolder)
让saveSuccess:Bool=NSKeyedArchiver.archiveRootObject(myDictionary,toFile:completeDataPath)
如果成功{
println(“保存字典的一些问题”)
}
返回saveSuccess
}
因此,我希望有一些通用类型的枚举,如“AnyEnumType”,以便以通用方式使用该函数:
func saveDictionary(myDictionary: Dictionary<AnyEnumType, AnyObject>, myFileName: String, myDataFolder: DataFolder) -> Bool {
...
}
func保存字典(myDictionary:Dictionary,myFileName:String,myDataFolder:DataFolder)->Bool{
...
}
当然,这会导致编译器错误“使用未声明的类型”AnyEnumType
我用typeAlias、TypePlaceholder
等做了很多尝试,但都没能实现
我如何实现这样的功能
func saveDictionary(myDictionary: Dictionary<AnyKeyType, AnyObject>, myFileName: String, myDataFolder: DataFolder) -> Bool { ..
}
func saveDictionary(myDictionary:Dictionary,myFileName:String,myDataFolder:DataFolder)->Bool{。。
}
通过声明这个泛型类型“AnyKeyType”遵循协议Hashable、equality、。。。
这使我能够使用字符串或Enum.Member作为键???类似的方法可能会奏效:
protocol EnumType {
typealias RawType
init?(rawValue: RawType)
var rawValue: RawType { get }
}
enum Hello: String, EnumType {
case Option1 = "Option1"
case Option2 = "Option2"
}
func toArchivableDictionaryWithEnumerationKeys<E: EnumType, T>(dictionary: Dictionary<E, T>) -> Dictionary<E.RawType, T> {
var result = Dictionary<E.RawType, T>()
// Tried to use reduce here, but couldn't make it work
for (key, value) in dictionary {
result[key.rawValue] = value
}
return result
}
func fromArchivedDictionaryWithEnumerationKeys<E: EnumType, T>(dictionary: Dictionary<E.RawType, T>) -> Dictionary<E, T>? {
var result = Dictionary<E, T>()
for (key, value) in dictionary {
if let enumKey = E(rawValue: key) {
result[enumKey] = value
} else {
return nil
}
}
return result
}
let dict = toArchivableDictionaryWithEnumerationKeys([Hello.Option1: "Bob"])
let data = NSKeyedArchiver.archivedDataWithRootObject(dict)
let value = NSKeyedUnarchiver.unarchiveObjectWithData(data) as Dictionary<String, String>
if let unarchived: Dictionary<Hello, String> = fromArchivedDictionaryWithEnumerationKeys(value) {
// Blah blah
}
协议枚举类型{
typealias原始类型
初始化?(rawValue:RawType)
var rawValue:RawType{get}
}
enum Hello:字符串,EnumType{
案例选项1=“选项1”
案例选项2=“选项2”
}
func to ArchivableDictionaryWithEnumerationKeys(字典:dictionary)->dictionary{
var result=Dictionary()
//尝试在此处使用reduce,但无法使其工作
用于字典中的(键、值){
结果[key.rawValue]=值
}
返回结果
}
func fromArchivedDictionaryWithEnumerationKeys(字典:dictionary)->字典?{
var result=Dictionary()
用于字典中的(键、值){
如果让enumKey=E(rawValue:key){
结果[enumKey]=值
}否则{
归零
}
}
返回结果
}
让dict=toArchivableDictionaryWithEnumerationKeys([Hello.Option1:“Bob”]))
让data=NSKeyedArchiver.archivedDataWithRootObject(dict)
让value=NSKeyedUnarchiver.unarchiveObjectWithData(data)作为字典
如果让未归档:Dictionary=fromArchivedDictionaryWithEnumerationKeys(值){
//废话
}
此外,您应该调用枚举HelloOptions
而不是HelloOptions
,并调用枚举值Option1
,而不是Option1
。Swift中的所有类型均应大写。你会注意到,Swift的设计师们虔诚地遵循着这个惯例。你也应该这样做
protocol EnumType {
typealias RawType
init?(rawValue: RawType)
var rawValue: RawType { get }
}
enum Hello: String, EnumType {
case Option1 = "Option1"
case Option2 = "Option2"
}
func toArchivableDictionaryWithEnumerationKeys<E: EnumType, T>(dictionary: Dictionary<E, T>) -> Dictionary<E.RawType, T> {
var result = Dictionary<E.RawType, T>()
// Tried to use reduce here, but couldn't make it work
for (key, value) in dictionary {
result[key.rawValue] = value
}
return result
}
func fromArchivedDictionaryWithEnumerationKeys<E: EnumType, T>(dictionary: Dictionary<E.RawType, T>) -> Dictionary<E, T>? {
var result = Dictionary<E, T>()
for (key, value) in dictionary {
if let enumKey = E(rawValue: key) {
result[enumKey] = value
} else {
return nil
}
}
return result
}
let dict = toArchivableDictionaryWithEnumerationKeys([Hello.Option1: "Bob"])
let data = NSKeyedArchiver.archivedDataWithRootObject(dict)
let value = NSKeyedUnarchiver.unarchiveObjectWithData(data) as Dictionary<String, String>
if let unarchived: Dictionary<Hello, String> = fromArchivedDictionaryWithEnumerationKeys(value) {
// Blah blah
}