如何在实例化期间访问属性(存储和计算)?

时间:2016-06-07 16:12:37

标签: swift initialization cs193p

我正在参加CS193课程。从video的确切时刻开始。

选项1:

class FaceView: UIView
{
    var scale: CGFloat = 0.90
    var mouthCurvature: Double = 1.0 

    private var skullRadius: CGFloat {
        return min(bounds.size.width, bounds.size.height) / 2 * scale
    }
 }

为什么我不能写

选项2:

class FaceView: UIView
{
    var scale: CGFloat = 0.90
    var mouthCurvature: Double = 1.0 

    private var skullRadius = min(bounds.size.width, bounds.size.height) / 2 * scale

 }

教授说并解释说,在初始化期间,您无法访问自己的属性,因此如果您执行选项2,则会收到错误消息:instance member 'bounds' cannot be used on type 'FaceView'

好的,但我们还不是在访问选项1中的实例成员'bounds`吗?有什么不同?或者访问是否正常,但是在初始化期间你不能使一个属性依赖于另一个

1 个答案:

答案 0 :(得分:1)

这是存储属性和计算属性之间的差异之一。

当实例化scale的实例时,将初始化存储的属性mouthCurvatureFaceView

在您的第一个示例中,skullRadius是一个计算属性,在您的FaceView实例在实例化后调用该属性时计算。

在第二个示例中,skullRadius是在实例化时初始化的存储属性。此时尚未提供其他属性,因为它们可能已初始化,也可能未初始化。

以下是在初始化期间如何引用其他属性的方法:

class test {
  let foo = 1 // stored property
  let bar = 2 // stored property
  let buzz: Int // stored property not initialized when other stored properties are initialized
  init() {
    buzz = foo + bar // initialized after other stored properties
  }
}

显示如何修改延迟属性的示例:

class Test {
  lazy var foo: Int = { return 5 }()
}

let test = Test()
print(test.foo) -> "5"
test.foo = 10
print(test.foo) -> "10"