我应该如何使用 Swift 枚举实现默认关联值?
How should I implement Default Associated Values with Swift Enums?
Swift 问题是有没有一种方法可以使枚举类型具有一个可以具有关联值的案例。
我有一个 API 可以提供可用的过滤器,API 不太可能但有可能会添加其他过滤器类型。因此,如果 API 发送未知的过滤器类型,我想将该信息与枚举相关联。
以下是我对此的不同想法。
我的前两次尝试没有编译通过。我的第三次尝试感觉有点笨拙。
有人有更好的方法吗?你认为我不应该使用枚举来解决这个问题吗?
typealias APIFilterIdentifier = String
/* Does Not Compile */
enum EnumTestAssociatedValeu: APIFilterIdentifier {
case Unknown(APIFilterIdentifier)
case Everyone = "everyone"
case Team = "myteam"
}
/* Does not compile */
enum EnumTestDefaultAssociatedValues: APIFilterIdentifier {
case Unknown(APIFilterIdentifier)
case Everyone(APIFilterIdentifier = "everyone")
case Team(APIFilterIdentifier = "myteam")
}
/* Compiles but is there a better way? */
enum EnumTestWithCustomInit {
case Unknown(APIFilterIdentifier)
case Everyone
case Team
init(filterIdentifier: APIFilterIdentifier) {
let everyone: APIFilterIdentifier = EnumTestWithCustomInit.everyoneFilterIdentifier
let team: APIFilterIdentifier = EnumTestWithCustomInit.teamFilterIdentifier
switch filterIdentifier {
case everyone:
self = .Everyone
case team:
self = .Team
default:
self = .Unknown(filterIdentifier)
}
}
func asIdentifer() -> APIFilterIdentifier {
switch self {
case .Everyone:
return EnumTestWithCustomInit.everyoneFilterIdentifier
case .Team:
return EnumTestWithCustomInit.teamFilterIdentifier
case .Unknown(let filterIdentifier):
return filterIdentifier
}
}
private static var everyoneFilterIdentifier: APIFilterIdentifier {
return "everyone"
}
private static var teamFilterIdentifier: APIFilterIdentifier {
return "myteam"
}
}
我知道这有点老了,但这对你想要的有用吗?
typealias FilterIdentifier = String
enum DefaultAPIFilters: FilterIdentifier {
case Everyone = "everyone"
case Team = "team"
}
enum APIFilters {
case Default(DefaultAPIFilters)
case Custom(FilterIdentifier)
}
let everyoneFilter = APIFilters.Default(.Everyone)
let teamFilter = APIFilters.Default(.Team)
let clownFilter = APIFilters.Custom("clowns_only")
扩展 Nathan Perry 的回应:
您可以添加一个
var underlyingString: String {
return getUnderlyingString(self)
}
到枚举。然后定义
func getUnderlyingString(apiFilter: APIFilters) -> String {
switch apiFilter {
case .Default(let defaultAPIFilter):
return defaultAPIFilter.rawValue
case .Custom(let custom):
return custom
}
}
根据这个回答:Default value for Enum in Swift
我推荐使用这种方法
public enum Result {
case passed(hint: String)
case failed(message: String)
static let passed: Self = .passed(hint: "")
}
let res: Result = Result.passed
Swift 问题是有没有一种方法可以使枚举类型具有一个可以具有关联值的案例。
我有一个 API 可以提供可用的过滤器,API 不太可能但有可能会添加其他过滤器类型。因此,如果 API 发送未知的过滤器类型,我想将该信息与枚举相关联。
以下是我对此的不同想法。
我的前两次尝试没有编译通过。我的第三次尝试感觉有点笨拙。
有人有更好的方法吗?你认为我不应该使用枚举来解决这个问题吗?
typealias APIFilterIdentifier = String
/* Does Not Compile */
enum EnumTestAssociatedValeu: APIFilterIdentifier {
case Unknown(APIFilterIdentifier)
case Everyone = "everyone"
case Team = "myteam"
}
/* Does not compile */
enum EnumTestDefaultAssociatedValues: APIFilterIdentifier {
case Unknown(APIFilterIdentifier)
case Everyone(APIFilterIdentifier = "everyone")
case Team(APIFilterIdentifier = "myteam")
}
/* Compiles but is there a better way? */
enum EnumTestWithCustomInit {
case Unknown(APIFilterIdentifier)
case Everyone
case Team
init(filterIdentifier: APIFilterIdentifier) {
let everyone: APIFilterIdentifier = EnumTestWithCustomInit.everyoneFilterIdentifier
let team: APIFilterIdentifier = EnumTestWithCustomInit.teamFilterIdentifier
switch filterIdentifier {
case everyone:
self = .Everyone
case team:
self = .Team
default:
self = .Unknown(filterIdentifier)
}
}
func asIdentifer() -> APIFilterIdentifier {
switch self {
case .Everyone:
return EnumTestWithCustomInit.everyoneFilterIdentifier
case .Team:
return EnumTestWithCustomInit.teamFilterIdentifier
case .Unknown(let filterIdentifier):
return filterIdentifier
}
}
private static var everyoneFilterIdentifier: APIFilterIdentifier {
return "everyone"
}
private static var teamFilterIdentifier: APIFilterIdentifier {
return "myteam"
}
}
我知道这有点老了,但这对你想要的有用吗?
typealias FilterIdentifier = String
enum DefaultAPIFilters: FilterIdentifier {
case Everyone = "everyone"
case Team = "team"
}
enum APIFilters {
case Default(DefaultAPIFilters)
case Custom(FilterIdentifier)
}
let everyoneFilter = APIFilters.Default(.Everyone)
let teamFilter = APIFilters.Default(.Team)
let clownFilter = APIFilters.Custom("clowns_only")
扩展 Nathan Perry 的回应:
您可以添加一个
var underlyingString: String {
return getUnderlyingString(self)
}
到枚举。然后定义
func getUnderlyingString(apiFilter: APIFilters) -> String {
switch apiFilter {
case .Default(let defaultAPIFilter):
return defaultAPIFilter.rawValue
case .Custom(let custom):
return custom
}
}
根据这个回答:Default value for Enum in Swift
我推荐使用这种方法
public enum Result {
case passed(hint: String)
case failed(message: String)
static let passed: Self = .passed(hint: "")
}
let res: Result = Result.passed