初始化IBOutlet时如何初始化变量?

时间:2018-12-16 15:53:32

标签: ios swift iboutlet initializer

我碰巧在新的iOS Swift应用程序中的一个UIViewControllers中编写了以下代码段。

var starButtonsCount = starButtons.count
@IBOutlet var starButtons: [UIButton]!

然后紧随错误之后的starButtonsCount变量声明旁边显示为红色。

  

错误:无法在属性中使用实例成员“ starButtons”   初始化器属性初始值设定项在“自我”可用之前运行。

因此我发现,通过将starButtonCount变量声明为lazy,我们可以解决此错误(在iOS App开发过程中是暂时的)。

我很想知道还有什么其他方法可以解决这个问题?

starButtonCount IBOutlet初始化后,是否可以触发starButtons的初始化?

4 个答案:

答案 0 :(得分:2)

awakeFromNib是一种方法,当.xib中的每个对象都已反序列化并且所有插座的图形都已连接时,将调用该方法。文档说:

  

声明

     

func awakeFromNib()

     

讨论

     

从笔尖存档重新创建的每个对象的消息,但仅在   存档中的所有对象均已加载并初始化。什么时候   一个对象收到awakeFromNib消息,它保证具有   其所有出口和操作连接都已建立。nib加载基础结构发送一个awakeFromNib

     

您必须调用awakeFromNib的超级实现,以使父类有机会执行其所需的任何其他初始化。尽管此方法的默认实现不执行任何操作,但是许多UIKit类提供了非空实现。您可以在自己的awakeFromNib方法中随时调用超级实现。

如:

class MyUIViewController : UIViewController {
    var starButtonsCount = 0
    @IBOutlet var starButtons: [UIButton]!
    override func awakeFromNib() {
        super.awakeFromNib()
        starButtonsCount = startButtons.count
    }
}

答案 1 :(得分:2)

还要注意,starButtonsCount不必是存储变量:

var starButtonsCount: Int {
   return starButtons.count
}

在这种情况下,直接使用starButtons.count可能会更好,因为该变量不会完全改善代码。

在通常情况下,除非存储派生状态可以提高性能(例如,缓存计算),否则不需要存储派生状态。

答案 2 :(得分:1)

另一种方式

var starButtonsCount:Int! 
@IBOutlet var starButtons: [UIButton]! { 
    didSet { 
         starButtonsCount = starButtons.count
    }
}

答案 3 :(得分:1)

简单的解决方案是一个常数

let starButtonsCount = 8 // or whatever the number of buttons is

IBOutlets在构建时已连接,因此按钮的数量在运行时不会改变。

您可以在viewDidLoad中添加一个断言行,以了解在应用程序的未来版本中是否更改了按钮的数量

assert(starButtons.count == starButtonsCount, "number of buttons has changed, adjust starButtonsCount")