Swift 协议的所有实现的返回类型
我有个小问题。我需要为一个函数指定一个返回值,该函数可以返回协议的每个实现。例如: 我的协议:Swift 协议的所有实现的返回类型,swift,protocols,Swift,Protocols,我有个小问题。我需要为一个函数指定一个返回值,该函数可以返回协议的每个实现。例如: 我的协议: protocol MyProtocol { //some functions } 实施: class ClassA: MyProtocol { } class ClassB: MyProtocol { } “问题”功能: func getClassByString(_ name: String) -> MyProtocol.Type { switch name {
protocol MyProtocol {
//some functions
}
实施:
class ClassA: MyProtocol {
}
class ClassB: MyProtocol {
}
“问题”功能:
func getClassByString(_ name: String) -> MyProtocol.Type {
switch name {
case "a":
return ClassA.self
case "b":
return ClassB.self
default:
return ClassC.self
}
}
//编辑:这是我需要结果的地方
final class Mapper<N: MyProtocol> {
public func map() -> N?{
if let klass = N.self as? MyProtocol.Type {
return klass as? N
}
return nil
}
}
final类映射器{
公共函数映射()->N{
如果让klass=N.self as?MyProtocol.Type{
将klass返回为?N
}
归零
}
}
用法:
let className = "a" //this String comes from a JSON
let result = getClassByString(className)
let mappingResult = Mapper<result>().map() //undeclared identifier 'result' error
let mappingResult = Mapper<ClassA>().map() //works but i do not know if it is ClassA
let className=“a”//此字符串来自JSON
让结果=getClassByString(className)
让mappingResult=Mapper().map()//未声明的标识符'result'错误
让mappingResult=Mapper().map()//工作,但我不知道它是否是ClassA
问题是,result
不是真正的ClassA.Type
,它应该是什么,现在是MyProtocol.Type
,我不能将它传递给下一个函数。
当我给出result
的ClassA.self的具体值时
一切正常。我无法将其转换为as!ClassA.self
,因为我不知道它是否必须是ClassA
或ClassB
或Class9000
所以问题是。函数
getClassByString()是否还有另一种返回类型,如MyProtocol.type
或者一种完全不同的方式来获得ClassA.Type
到result
?我认为你这里的问题与你描述的不完全一样-你的例子中的result
看起来确实是一个ClassA.Type
在操场上,但我怀疑的问题是你接下来该怎么处理它。您的协议没有说明如何以通用方式实例化此类类型,因此无法实例化返回的类型
我对您的示例做了一些更改,现在它可以工作了
protocol MyProtocol {
//some functions
init() // To instantiate generically, there MUST be an accepted pattern for init()
}
class ClassA: MyProtocol {
required init() {}
}
class ClassB: MyProtocol {
required init() {}
}
class ClassC: MyProtocol {
required init() {}
}
func getClassByString(_ name: String) -> MyProtocol.Type {
switch name {
case "a":
return ClassA.self
case "b":
return ClassB.self
default:
return ClassC.self
}
}
let className = "a" //this String comes from a JSON
let result = getClassByString(className) // ClassA.Type
let a = result.init() // ClassA
请注意,尽管
type(of:a)
将报告ClassA
,但我们可能不会调用ClassA
的实例方法,例如a
上的MyProtocol
中没有蓝图的。假设ClassA
有一个方法foo()->()
,那么a.foo()
将产生错误消息“error:typeMyProtocol
的值没有成员foo
”。但我想这是意料之中的,否则Swift的静态类型在这种情况下会失败(编译时未确定)。@dfri-这正是我的观点-调用init()
it A)必须在协议中指定,B)必须在实现中必需,
,事实上,我已经明确指出了这一点(主要针对OP)我相信OP正在试图解决XY问题,使用的方法不适合Swift这样的静态类型语言。最后,OP将只能使用MyProtocol
分层类型,因为我们在编译时永远无法知道a
的具体类型,这导致OP对(a as!ClassA).foo()进行推理。我推测,朝这个方向进行将导致OP的代码推理,并且他/她可能希望在继续尝试“运行时键入”之前重新访问原始问题(…可能值得一提的是,即使我们“一般地”实例化a
)(由蓝图提供的init
)上面,这还没有结束:a
仍然不是一个具体的ClassA
,如果不熟悉Swift的静态类型本质,这可能会从上面答案中的最后一段代码中被误解。谢谢你的回答。我编辑了我的问题,以便更清楚地说明我需要什么result
。