我有一个协议P,它返回对象的副本:
protocol P {
func copy() -> Self
}
和一个实现P的类C:
class C : P {
func copy() -> Self {
return C()
}
}
但是,是否Self
在出现以下错误时放入返回值:
无法将类型“ C”的返回表达式转换为类型“ Self”
我也试着回来C
。
class C : P {
func copy() -> C {
return C()
}
}
这导致以下错误:
非最终类“ C”中的方法“ copy()”必须返回
Self
以符合协议“ P”
除了我class C
以final
ie做前缀的情况外,没有任何作用:
final class C : P {
func copy() -> C {
return C()
}
}
但是,如果我想对C进行子类化,那么将无济于事。有没有办法解决?
问题是您要保证编译器无法证明您会保留。
因此,您创建了以下承诺:调用copy()
将返回其自身的类型,并进行完全初始化。
但是随后您实现了copy()
这种方式:
func copy() -> Self {
return C()
}
现在我是一个不会重写的子类copy()
。然后返回C
,而不是完全初始化的Self
(我保证)。那就不好了 怎么样:
func copy() -> Self {
return Self()
}
好吧,那不会编译,但是即使编译了,也没有好处。子类可能没有琐碎的构造函数,因此D()
甚至可能不合法。(尽管请参见下文。)
好的,怎么样:
func copy() -> C {
return C()
}
是的,但这不会返回Self
。它返回C
。您仍然没有遵守诺言。
“但是ObjC可以做到!”
好吧,有点。主要是因为它并不关心您是否像Swift那样信守诺言。如果无法copyWithZone:
在子类中实现,则可能无法完全初始化对象。编译器甚至不会警告您已完成该操作。
“但是ObjC中的大多数内容都可以翻译成Swift,而ObjC可以NSCopying
。” 是的,它的定义方式如下:
func copy() -> AnyObject!
因此,您可以执行相同操作(此处没有理由!):
protocol Copyable {
func copy() -> AnyObject
}
那就是“我不保证你会得到什么。” 您还可以说:
protocol Copyable {
func copy() -> Copyable
}
那是您可以做出的承诺。
但是我们可以考虑一下C ++,并记住我们 可以
做出承诺。我们可以保证我们和我们所有的子类都将实现特定类型的初始化器,而Swift将强制执行该初始化器(因此可以证明我们说的是实话):
protocol Copyable {
init(copy: Self)
}
class C : Copyable {
required init(copy: C) {
// Perform your copying here.
}
}
这就是您应该执行复制的方式。
我们可以进一步迈出这一步,但是它使用了dynamicType
,而且我还没有对其进行广泛的测试以确保它始终是我们想要的,但是它应该是正确的:
protocol Copyable {
func copy() -> Self
init(copy: Self)
}
class C : Copyable {
func copy() -> Self {
return self.dynamicType(copy: self)
}
required init(copy: C) {
// Perform your copying here.
}
}
在这里,我们保证有一个初始化程序为我们执行拷贝,然后我们可以在运行时确定要调用的那个,从而为我们提供了您要查找的方法语法。
问题内容: 我正在使用swift 2.0,我有一个协议和对该协议的扩展来创建方法的默认实现,代码如下: 稍后,我在代码中尝试调用此方法,并收到一条错误消息: “不能在不可变值上使用变异成员:’自身’是不可变的” 代码如下: 我唯一想到的是这种情况下的“ Self”是协议,而不是类。但是,我必须缺少一些东西才能使该概念起作用。该协议定义的方法的默认实现,该方法还可以编辑同一协议定义的值。 谢谢您的帮
cmf_get_domain() 功能 返回带协议的域名 参数 无 返回 string
返回当前运行的whisper版本。 调用: web3.shh.getVersion([callback]) 参数: callback:Function - 可选的回调函数,其第一个参数为错误对象,第二个参数为结果 返回值: String - 当前运行中的whisper版本 示例代码: web3.shh.getVersion() .then(console.log); > "5.0"
返回节点旳以太坊协议版本。 调用: web3.eth.getProtocolVersion([callback]) 返回值: 一个Promise对象,其解析值为协议版本字符串。 示例代码: web3.eth.getProtocolVersion().then(console.log); > "63"
函数也可以将值与控件一起返回给调用者。 这些函数称为returning functions 。 语法 (Syntax) return_type function_name(){ //statements return value; } return_type可以是任何有效的数据类型。 return语句是可选的。 我没有指定函数返回null; 返回值的数据类型必须与函数的返
问题内容: 当我尝试在http://golang.org/pkg/net/http/#example_Get上运行此示例时,它返回以下错误 2009/11/10 23:00:00获取http://www.google.com/robots.txt:拨打tcp:协议不可用 知道为什么吗? 问题答案: Go Playground不允许HTTP请求。这与代码无关。这是操场强制执行的安全预防措施。