1

I have a lazy variable that is not initialised:

lazy var time: () -> String = {
    return String(describing: Date())
}

Whenever I call time() I get a new Date. So it seems like it behaves exactly like:

var time: () -> String {
    return {
        return String(describing: Date())
    }
}

In this context, is it bad practice just to use the lazy closure, because then I don't have to write two return-statements in a row or do I miss something?

6
  • Your lazy var time is initialized only once – to a closure that, when called, returns a string with the current date. Commented Feb 24, 2018 at 16:18
  • @MartinR So in this case, since the content of the closure is still dynamic, it is basically a function that I can pass around? Commented Feb 24, 2018 at 16:23
  • Why not just say func time() -> String { return String(describing: Date()) }? Commented Feb 24, 2018 at 16:24
  • 1
    Functions are closures in Swift. – What behavior is it that you actually want to achieve? Commented Feb 24, 2018 at 16:25
  • @Hamish Well, my original code sample is a bit more complicated. The closure must be passed around and stored in an array. So a normal variable is not sufficient enough. Commented Feb 24, 2018 at 16:26

1 Answer 1

2

You don't need two return statements in a row nor do you need a lazy closure. Why not just do:

let time: () -> String = {
    return String(describing: Date())
}

Or just replace this whole thing with a method:

func time() -> String {
    return String(describing: Date())
}

One reason why you might want to use a closure here is that you want other parts of your code to change the value of the closure. If that's the case, just do it like the first snippet, otherwise I don't think anything is preventing you from writing a method. You can pass a method around just like a closure, because methods are a kind of closure!

Lazy variables are really needed when initializing them takes much resources. Creating closures tend to be cheap.

Sign up to request clarification or add additional context in comments.

3 Comments

Just to amplify the point here: it is bad practice to make this lazy and it's bad practice to make it a property. It should be a function, as in the last example. It's bad practice to make it lazy because there's no reason to delay the initialization. (It's like writing lazy var x = 4; it's legal but pointless.) It shouldn't be a property because it doesn't act like a property. Despite nothing changing about the struct, the value is different every time it's called. This isn't "property-like."
Converting Date to String using String(describing:) should only be used when debugging. Never do that for any other situation. Use a DateFormatter for all other cases. Use date/timeStyle if showing the date to a user. Use dateFormat if a fixed format is needed to send to a server, for example.
@maddy You're right. I just chose this example for simplicity reasons, to demonstrate that the content of lazy is not stored like it would be, if the lazy variable would have returned a non closure.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.