Are lazy vars in Swift computed more than once?

Doug Smith picture Doug Smith · Oct 19, 2014 · Viewed 8.1k times · Source

Are lazy vars in Swift computed more than once? I was under the impression that they replaced the:

if (instanceVariable) {
    return instanceVariable;
}

// set up variable that has not been initialized

Paradigm from Objective-C (lazy instantiation).

Is that what they do? Basically only called once the first time the app asks for the variable, then just returns what was calculated?

Or does it get called each time like a normal computed property?

The reason I ask is because I basically want a computed property in Swift that can access other instance variables. Say I have a variable called "fullName" and it just concatenates firstName and lastName. How would I do that in Swift? It seems like lazy vars are the only way to go, as in normal computed vars (non-lazy) I can't access other instance variables.

So basically:

Do lazy vars in Swift get called more than once? If so, how do I create a computed variable that can access instance variables? If not, if I only want a variable to be computed once for performance reasons, how do I do this?

Answer

Aaron Brager picture Aaron Brager · Oct 19, 2014

lazy vars are only calculated once, the first time you use them. After that, they're just like a normal variable.

This is easy to test in a playground:

class LazyExample {
    var firstName = "John"
    var lastName = "Smith"
    lazy var lazyFullName : String = {
        [unowned self] in
        return "\(self.firstName) \(self.lastName)"
    }()
}

let lazyInstance = LazyExample()

println(lazyInstance.lazyFullName)
// John Smith

lazyInstance.firstName = "Jane"

println(lazyInstance.lazyFullName)
// John Smith

lazyInstance.lazyFullName = "???"

println(lazyInstance.lazyFullName)
// ???

If you'll want to recalculate it later, use a computed property (with a backing variable, if it's expensive) - just like you did in Objective-C.