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?
No, lazy properties are initialized only once. If you set a new value, or reset to nil (for optional properties), the lazy initializer is not invoked again.
I think what you need is a computed property - it's not backed by a stored property, so it is not involved in the initialization, and as such you can refer other instance properties.
Why do you say that "normal computed vars (non-lazy) I can't access other instance variables"?
Answers stating that a lazy var can only be computed once are not true. From the documentation at https://docs.swift.org/swift-book/LanguageGuide/Properties.html, the following is stated:
Also, please watch this talk: https://developer.apple.com/videos/play/wwdc2016/720/. At around 17:00, the following screen appears:
That talk gives you more insight about multithreading, I recommend you to watch it!
All the other answers are correct, I would just like to add that Apple warns about
lazy
variables and concurrency:lazy var
s 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:
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.